我有以下xml文件:
<?xml version="1.0" encoding="UTF-8" standalone="no" ?>
<config>
<a>
<b>
<param>p1</param>
<param>p2</param>
</b>
</a>
</config>
和获取我的节点参数的xpath代码:
Document doc = ...;
XPath xpath = XPathFactory.newInstance().newXPath();
XPathExpression expr = xpath.compile("/config/a/b");
Object o = expr.evaluate(doc, XPathConstants.NODESET);
NodeList list = (NodeList) o;
但事实证明节点列表(列表)有5个孩子,包括"\t\n"
,而不是只有两个。我的代码有问题吗?我怎样才能得到我的两个节点?
谢谢!
答案 0 :(得分:5)
当您选择/config/a/b/
时,您正在选择 b
的所有子项,其中包括三个文本节点和两个元素。也就是说,考虑到上面的XML,只显示有问题的片段:
<b>
<param>p1</param>
<param>p2</param>
</b>
第一个孩子是<b>
之后和<param>p1 ...
之后的文本(空白)。第二个孩子是第一个param
元素。第三个子节点是两个param
元素之间的文本(空白)。等等。 XML中不会忽略空格,尽管许多处理XML的形式都忽略它。
您有几个选择:
你可以这样做:
for (int i = 0; i < nodes.getLength(); i++) {
if (nodes.item(i).getNodeType() != Node.TEXT_NODE) {
System.out.println(nodes.item(i).getNodeValue());
}
}
您可以使用节点类型仅选择元素节点,或删除文本节点。
答案 1 :(得分:4)
所以xpath看起来像:
/config/a/b/*/text()
。
并输出:
for (int i = 0; i < nodes.getLength(); i++) {
System.out.println(nodes.item(i).getNodeValue());
}
将如预期的那样:p1和p2
答案 2 :(得分:2)
怎么样
/config/a/b/*/text()/..
答案 3 :(得分:1)
import org.w3c.dom.*;
import javax.xml.xpath.*;
import javax.xml.parsers.*;
import java.io.IOException;
import org.xml.sax.SAXException;
public class TestClient_XPath {
public static void main(String[] args) throws ParserConfigurationException,
SAXException, IOException, XPathExpressionException {
DocumentBuilderFactory domFactory = DocumentBuilderFactory
.newInstance();
domFactory.setNamespaceAware(true);
DocumentBuilder builder = domFactory.newDocumentBuilder();
Document doc = builder.parse("yourfile.xml");
XPath xpath = XPathFactory.newInstance().newXPath();
XPathExpression xPathExpression = xpath.compile("/a/b/c");
Object res = xPathExpression.evaluate(doc);
System.out.println(res.toString());
}
}
Xalan和Xerces似乎嵌入在rt.jar中。
不要包含xerces和xalan libs。
答案 4 :(得分:0)
我不确定但不应该 / config / a / b 只返回 b ? / config / a / b / param 应返回两个 param 节点...
问题的观点可能是问题吗?当然,您将返回结果节点及其所有子节点。所以你只需要看第一个元素,而不是它的子元素。
但我完全错了,因为我通常只是使用Xpath来浏览DOM树(HtmlUnit)。