我是使用XPath的新手,这可能是一个基本问题。请耐心帮助我解决问题。我有一个像这样的XML文件:
<RootNode>
<FirstChild>
<Element attribute1="abc" attribute2="xyz">Data</Element>
<FirstChild>
</RootNode>
我可以使用以下内容验证<Element>
标记的存在。
//Element[@attribute1="abc" and @attribute2="xyz"]
现在我还要检查字符串"Data"
的标记值。为实现这一目标,我被告知要使用:
//Element[@attribute1="abc" and @attribute2="xyz" and Data]
当我使用后面的表达式时,我收到以下错误:
断言失败消息:没有匹配的节点
//Element[@attribute1="abc" and @attribute2="xyz" and Data]
请告诉我我使用的XPath表达式是否有效。如果不是有效的XPath表达式?
答案 0 :(得分:306)
以下条件:
//Element[@attribute1="abc" and @attribute2="xyz" and Data]
检查Element中元素Data的存在,而不是元素值Data。
相反,您可以使用
//Element[@attribute1="abc" and @attribute2="xyz" and text()="Data"]
答案 1 :(得分:19)
.
我添加此答案的原因是我想解释text()
和[]
的关系。
首先使用*[number]
时,只有两种类型的数据:
*[bool]
从节点集boolean()
从node-set 在这种情况下,函数text()
将值计算为布尔值,并且有一条规则:
始终根据上下文评估过滤器。
当您需要将.
或"Data"
与字符串string()
进行比较时,它首先使用string()
函数将这些函数转换为字符串类型,而不是获取布尔结果。
有关string()
的两条重要规则:
text()
函数通过返回节点集中第一个节点的字符串值将节点集转换为字符串,这在某些情况下可能会产生意外结果。
["Data"]
是返回节点集的相对路径,包含当前节点(上下文节点)的所有文本节点,如string(["Data"])
。
当它由string()
计算时,它将返回node-set的第一个节点,因此只有当节点集中只有一个文本节点时才能获得“Data”。
如果希望['a', 'b']
函数连接所有子文本,则必须传递单个节点而不是节点集。
例如,我们获得了一个节点集string(parent)
,您可以将父节点传递给'ab'
,这将返回string(.)
,并返回原因"Data"
case将返回串联字符串counter
。
只有存在文本节点时,两种方式才会得到相同的结果。