XML 仍是企業級整合、配置檔、報文交換的常見格式。Java 生態系提供多種解析器,各有優劣。本文系統比較 DOM、SAX、JDOM、DOM4J 四大方案的原理、效能、適用場景,並附完整程式碼範例助你快速選型。
| 方案 | 解析模型 | 記憶體佔用 | 速度 | 易用度 | 適合場景 |
|---|---|---|---|---|---|
| DOM (JAXP) | 樹狀結構,一次載入整份文檔 | 高(正比文檔大小) | 中 | 高(API 直觀) | 小檔案、需隨機存取、頻繁修改結構 |
| SAX | 事件驅動,串流式單向讀取 | 極低(不載入樹) | 最快 | 低(需自行維護狀態) | 大檔案、唯讀、單次遍歷、記憶體受限 |
| JDOM | 樹狀,Java 原生 API(Collection、具體類) | 高 | 中偏慢 | 最高(語法簡潔) | 中小檔案、追求開發效率、不需 XPath |
| DOM4J | 樹狀 + 事件混合,支援 XPath、Schema | 中高(可選串流模式) | 最快(樹模式下) | 高(功能豐富) | 企業級專案、大檔案、需 XPath/Schema、Hibernate 等整合 |
DocumentBuilderFactory、Document、NodeList。ContentHandler、DefaultHandler。List、Element 具體類而非介面。SAXBuilder 建樹、XPath 支援較弱、輸出格式化簡單。SAXReader)、並行支援 DOM4J API 與標準 DOM 介面。<?xml version="1.0" encoding="GB2312"?>
<RESULT>
<VALUE>
<NO>A1234</NO>
<ADDR>四川省XX縣XX鎮XX路X段XX號</ADDR>
</VALUE>
<VALUE>
<NO>B1234</NO>
<ADDR>四川省XX市XX鄉XX村XX組</ADDR>
</VALUE>
</RESULT>
DocumentBuilderFactory f = DocumentBuilderFactory.newInstance();
Document doc = f.newDocumentBuilder().parse(new File("data.xml"));
NodeList list = doc.getElementsByTagName("VALUE");
for (int i = 0; i < list.getLength(); i++) {
Element e = (Element) list.item(i);
System.out.println(e.getElementsByTagName("NO").item(0).getTextContent()
+ " | " + e.getElementsByTagName("ADDR").item(0).getTextContent());
}
public class SaxHandler extends DefaultHandler {
private String currentTag;
@Override public void startElement(String u, String l, String q, Attributes a) {
currentTag = q;
}
@Override public void characters(char[] ch, int start, int len) {
String val = new String(ch, start, len);
if ("NO".equals(currentTag)) System.out.print("NO: " + val + " | ");
else if ("ADDR".equals(currentTag)) System.out.println("ADDR: " + val);
}
}
// 使用
SAXParserFactory.newInstance().newSAXParser().parse(new File("data.xml"), new SaxHandler());
SAXBuilder builder = new SAXBuilder();
Document doc = builder.build(new File("data.xml"));
Element root = doc.getRootElement();
for (Element v : root.getChildren("VALUE")) {
System.out.println(v.getChildText("NO") + " | " + v.getChildText("ADDR"));
}
SAXReader reader = new SAXReader();
Document doc = reader.read(new File("data.xml"));
for (Iterator<Element> it = doc.getRootElement().elementIterator("VALUE"); it.hasNext(); ) {
Element v = it.next();
System.out.println(v.elementText("NO") + " | " + v.elementText("ADDR"));
}
現代 Java 專案中,DOM4J 仍是綜合表現最佳的選擇(Hibernate、Spring 內部皆採用)。若專案極度輕量或 Android 環境,可考慮標準 JAXP DOM/SAX 以避免額外依賴。理解四者核心差異,才能在效能與維護性間取得最佳平衡。