如何在Java中检查节点是否具有一个或多个具有XPath的特定属性?

时间:2012-07-20 06:22:00

标签: java xml xpath

我想获得包含以下属性之一的每个子节点:type,ref,base。每个属性的值并不重要,我只想检查属性是否存在。

我现在就是这样做的:

private void addRequiredNodeAndChildren(Node n) {    
            XPath xpath = XPathFactory.newInstance().newXPath();
            String expression = "*//*[@base or @ref or @type]";
            XPathExpression expr = xpath.compile(expression);
            NodeList referList = (NodeList) expr.evaluate(n, XPathConstants.NODESET);
            ..
}

这个表达式工作正常但在一个案例中我没有得到所有预期的节点:

 <xs:complexType name="ListElement">
        <xs:annotation>
            <xs:documentation>
            </xs:documentation>
        </xs:annotation>
        <xs:attribute name="transferMode" type="myprefix:dataTransferMode"
            use="optional">
            <xs:annotation>
                <xs:documentation>Documentation for attribute
                </xs:documentation>
            </xs:annotation>
        </xs:attribute>
    </xs:complexType>

我希望得到带有上述表达式的节点,但不幸的是我无法得到它。将表达式更改为

//*[@base or @ref or @type] 

也没有帮助,因为我从XML获得了每个节点的一个属性,但我想只得到给定节点n的子节点。我也试过

*//*[@base] or *//*[@ref] or *//*[@type]

作为表达,但也没有效果。

有没有人想过如何解决我的问题?

3 个答案:

答案 0 :(得分:0)

  

//*[@base or @ref or @type]   也没有帮助,因为我从XML获得了每个节点的一个属性,但我想只得到给定节点的子节点n

那是因为'//'搜索整个文档。你的谓词是正确的,但你过滤的序列是错误的。要获取上下文节点的子节点,请使用

*[@base or @ref or @type]

顺便提一下,如果您尝试列出XSD中包含引用架构中其他声明的QNames的所有属性,则列表不完整。

答案 1 :(得分:0)

看来你想要的是:

*[descendant-or-self::*[@base or @ref or @type] ]

答案 2 :(得分:0)

谢谢大家的帮助!

我找到了一个不太漂亮的解决方案,但至少它有效:

*[@base or @ref or @type] | *//*[@base or @ref or @type]

编辑:我改编了Dimitre Novatchev's解决方案,它也解决了这个问题:

descendant-or-self::*[@base or @ref or @type]