如果您的XML 包含命名空間,如以下範例:
<?xml version="1.0" encoding="UTF-8" standalone="yes"?> <workbook xmlns="http://schemas.openxmlformats.org/spreadsheetml/2006/main" xmlns:r="http://schemas.openxmlformats.org/officeDocument/2006/relationships"> <sheets> <sheet name="Sheet1" sheetId="1" r:id="rId1"/> </sheets> </workbook>
使用XPath 查詢時可能會遇到問題,例如「/workbook/sheets/sheet[1]」。這是因為元素綁定到命名空間,而您的 XPath 正在預設的匿名命名空間中尋找元素。
有在XPath 查詢中處理命名空間的多種方法:
建議的方法是使用前綴註冊命名空間。這簡化了XPath 開發和維護:
NamespaceContext namespaceContext = new NamespaceContext() { @Override public String getNamespaceURI(String prefix) { if ("xssf".equals(prefix)) { return "http://schemas.openxmlformats.org/spreadsheetml/2006/main"; } return null; } @Override public String getPrefix(String namespaceURI) { return null; } @Override public Iterator getPrefixes(String namespaceURI) { return null; } }; XPath xpath = XPathFactory.newInstance().newXPath(); xpath.setNamespaceContext(namespaceContext);
透過此設置,您可以使用簡化的XPath 查詢:
/xssf:workbook/xssf:sheets/xssf:sheet[1]
如果您不想使用命名空間前綴,您可以製作使用通用匹配的XPath 表達式謂詞過濾器:
/*[local-name()='workbook' and namespace-uri()='http://schemas.openxmlformats.org/spreadsheetml/2006/main'] /*[local-name()='sheets' and namespace-uri()='http://schemas.openxmlformats.org/spreadsheetml/2006/main'] /*[local-name()='sheet' and namespace-uri()='http://schemas.openxmlformats.org/spreadsheetml/2006/main'][1]
此方法會產生冗長的XPath 表達式,可能難以閱讀和維護。
您也可以透過僅在本地匹配來忽略命名空間name:
/*[local-name()='workbook']/*[local-name()='sheets']/*[local-name()='sheet'][1]
但是,在跨在不同命名空間使用相同本地名稱的混合詞彙的情況下,此方法有選擇錯誤元素的風險。
以上是當 XML 包含命名空間時,如何處理 XPath 查詢中的命名空間?的詳細內容。更多資訊請關注PHP中文網其他相關文章!