我想检查文档中是否有内联样式表,但我不确定如何选择元素的后代属性,因为“样式”属性可以附加到正文元素中的任何元素。这是我写的当前 xpath:
descendant::@*[self::@style]
但是解析器抛出错误说:“轴名称后出现意外的标记“@””。谁能告诉我如何解决它或有另一种方法可以做到这一点?谢谢!
我想检查文档中是否有内联样式表,但我不确定如何选择元素的后代属性,因为“样式”属性可以附加到正文元素中的任何元素。这是我写的当前 xpath:
descendant::@*[self::@style]
但是解析器抛出错误说:“轴名称后出现意外的标记“@””。谁能告诉我如何解决它或有另一种方法可以做到这一点?谢谢!
@style
因此,您正在文档中的任何位置查找具有我认为的属性的任何元素。
如果您想要包含您想要的属性的元素,请执行以下操作:
descendant::*[@style]
这将返回当前节点的所有具有@style
属性的后代元素。如果你想要属性本身,你最好使用类似的东西:
descendant::*[@style]/@style
这将为您找到所有样式属性本身。
使用这个 XPath: //@style
,它将选择所有属性style
@Kirill 给出了关于如何修复的正确答案
descendant::@*[self::@style]
通过使用
//@style
但是对于那些想知道为什么初始 XPath 不起作用以及是否有使用self::
它的变体的人来说......
请记住,这@
是attribute::
轴的缩写。self::@foo
的简写也是如此self::attribute::foo
。但从句法上讲,定位步骤中只能有一个轴。这就是解析器拒绝的原因self::@style
:它有两个轴。
这里还有一些有趣的事情正在发生。您可能认为可以按如下方式修复表达式:
//@*[self::style]
(暂时忽略这样一个事实,即这不必要地比//@style
. style
//@*[not(self::style)]
此表达式解析并运行没有错误。第一部分//@*
匹配文档中的所有属性节点。你可能会认为(就像我一样)只要它的上下文节点是一个属性,谓词[self::style]
就会评估为一个真值。style
但我们会错的。如果我们尝试一下,我们会得到一个空的节点集。为什么?如果上下文节点是属性节点,并且self::
轴仅包含上下文节点,并且属性的名称与后面的名称匹配,self::
那么谓词中的表达式不应该将该属性节点作为其结果吗?
在页。XSLT 2.0 和 XPath 2.0(第 4 版)的 1228,Self Axis 的词汇表定义解释:
自轴的主节点种类是elements,这意味着当上下文节点是一个属性时,表单的一个轴步
self::*
或self::xyz
不会选择该属性[粗体强调我的]。
但是,在 XPath 2.0 中,您可以使用self::attribute(style)
. 即您可以使用 KindTest 而不是 NameTest。
Michael Kay 详细介绍了 p 上的 NameTest 可以匹配哪些类型的节点的规则。695。