正确XPath表达式是//[not(@)],用于匹配文档中所有无任何属性的元素;not(@*)在属性节点集为空时返回true,故可精准筛选如A和D等无属性元素。

要选择所有没有属性的元素,XPath 表达式是://*[@* = ''] ❌ —— 这是常见误解,**不正确**。
正确写法是:/*[not(@*)](匹配根元素且无属性)
更通用的是://*[not(@*)]
为什么用 not(@*)?
@* 表示“任意属性”,它是一个节点集。只要有至少一个属性,@* 就非空;not(@*) 在节点集为空时返回 true,即该元素**完全不带任何属性**。
- ✅ 匹配:
、hello - ❌ 不匹配:
、...(哪怕只有一个属性也不行)
注意作用域和常见误区
//*[not(@*)] 会匹配文档中所有层级无属性的元素(包括 html、body、div、p、span 等),但不包括文本节点、注释等。
- 如果只想选特定标签(比如只选无属性的
div),写成://div[not(@*)] -
@*不包含命名空间声明(如xmlns),但在大多数 HTML 解析器中,XML 命名空间属性通常不被视为普通属性,所以一般不受影响 - 不要用
count(@*) = 0—— 虽然逻辑等价,但not(@*)更简洁、性能略优,且兼容性更好(尤其在 XPath 1.0)
实际小例子
对如下 HTML 片段:
ABC
D
执行 D//*[not(@*)] 会选出:
→ 和 (共 2 个元素)
基本上就这些。不复杂但容易忽略括号和 not 的位置。










