简明XPath

作者 uunnfly 日期 2019-03-23
简明XPath

XPath是一门在XML文档中查找信息的语言,当然也可以在html中使用

XPath十分简单:你只要把条件连在一起。在节点的集合里选中符合条件的,再作为新的集合继续这个过程。

/ vs []

  • /之后的条件意思是:下一步选择匹配的子节点
  • []之内的条件意思是:在原有的集合中排除那些不符合条件的节点,也就是只选择符合[]内条件的节点

举个例子:

1
2
3
4
5
6
<foo>
<bar>test1</bar>
</foo>
<foo>
test2
</foo>

  • /foo/bar
  1. 从根节点开始
  2. 接着/foo:根节点下有两个子节点,比较一下,把所有的foo元素组成新的集合供下一步使用
  3. 接着/bar: 抓取每个节点的子节点,如果该子节点是bar则把该子节点放入新的集合
  4. 得出结果:<bar>test1</bar>
  • /foo[bar]
  1. 从根节点开始
  2. 接着/foo:根节点下有两个子节点,比较一下,把所有的foo元素组成新的集合供下一步使用
  3. 接着/bar: 抓取每个节点的子节点,如果该子节点有bar元素则把该节点放入新的集合
  4. 得出结果:<foo><bar>test1</bar></foo>

[]内也可以写坐标: [1] 也就是[position() = 1],会取得符合条件的第一个元素

::

轴是用::分割的前缀,轴指定相对于当前节点集的任意元素,既可以是子节点,又可以是当前节点、兄弟节点或者其祖先节点

举个例子:

/foo/following-sibling:bar

  1. 从根节点开始
  2. 接着/foo:检查节点集中的每个节点(这里就一个根节点)的子节点,把所有的foo元素组成新的集合供下一步使用
  3. 接着/following-sibling::bar: 检查节点集中的每个节点的同级节点,如果存在同级节点是bar则把该节点放入新的集合(此处实际没什么作用,还是取得所有的foo节点)

实际上/foo/bar意思是/child::foo/child::bar, /foo[bar] 意思是 /child::foo[child::bar]

此外,还有一些语法糖:attribute::foo 可以写成 @foo, /descendant-or-self::foo可以写成//foo,也就是说//表示自身或者任意后代。

. vs /

  • . 是相对路径,指当前节点
  • / 是绝对路径,从根节点开始

注意:在scrapy中使用xpath时

1
2
3
users = response.xpath("//*[id='user']")
for user in users:
item['passwd'] = user.xpath(".//*[id='passwd']")

user.xpath(".//*[id='passwd']")必须有这个点.,否则会找出文档中所有符合条件的节点,而不是当前user下的集合

参考资料

Concise XPath
XPath 教程