XPath - node()和text()之间的区别

Pzt*_*tar 57 xml xpath expression

我无法理解之间的差异text()node().根据我的理解,在这种情况下text(),标签之间的任何东西<item>apple</item>都是苹果.节点将是节点实际上的任何节点,这将是项目

但后来我被分配了一些工作,它要求我"选择生产中所有项目的文本",另一个问题是"选择所有部门中的所有经理节点"

输出如何看起来text()与之相反node()

XML片段:

<produce>
 <item>apple</item>
 <item>banana</item>
 <item>pepper</item>
</produce>

<department>
 <phone>123-456-7891</phone>
 <manager>John</manager>
</department>
Run Code Online (Sandbox Code Playgroud)

当然,有更多的部门和更多的经理,但这只是一小段代码.

任何帮助将非常感激!

Tom*_*lak 123

text()并且node()是XPath术语中的节点测试(比较).

节点测试对节点(在一个轴上,准确地说)节点进行操作,并返回某种类型的节点.如果未提及child轴,则默认采用轴.

有各种节点测试:

  • node()匹配任何节点(所有节点的最少特定节点测试)
  • text()仅匹配文本节点
  • comment()匹配评论节点
  • *匹配任何元素节点
  • foo 匹配任何名为的元素节点 "foo"
  • processing-instruction()匹配PI节点(它们看起来像<?name value?>).
  • 附注:*也匹配属性节点,但仅沿attribute轴.@*是一个简写attribute::*.属性不是child轴的一部分,这就是法线*不选择它们的原因.

这个XML文档:

<produce>
    <item>apple</item>
    <item>banana</item>
    <item>pepper</item>
</produce>
Run Code Online (Sandbox Code Playgroud)

代表以下DOM(简化):

root node
   element node (name="produce")
      text node (value="\n    ")
      element node (name="item")
         text node (value="apple")
      text node (value="\n    ")
      element node (name="item")
         text node (value="banana")
      text node (value="\n    ")
      element node (name="item")
         text node (value="pepper")
      text node (value="\n")

所以使用XPath:

  • / 选择根节点
  • /produce如果它具有名称,则选择根节点的子元素"produce"(这称为文档元素 ;它表示文档本身.文档元素和根节点经常混淆,但它们不是同一个东西.)
  • /produce/node()选择任何类型的子节点的下方/produce/(即,所有7个孩子)
  • /produce/text() 选择4(!)仅空白文本节点
  • /produce/item[1] 选择名为的第一个子元素 "item"
  • /produce/item[1]/text()选择所有子文本节点(只有一个 - "苹果" - 在这种情况下)

等等.

所以,你的问题

  • "选择生产中所有项目的文本" /produce/item/text()(选择3个节点)
  • "选择所有部门中的所有管理器节点" //department/manager(选择1个节点)

笔记

  • XPath中的默认child轴.您可以通过为不同的轴名称添加前缀来更改轴.例如://item/ancestor::produce
  • 元素节点具有文​​本值.评估元素节点时,将返回其文本内容.在本例的情况下,/produce/item[1]/text()string(/produce/item[1])将是相同的.
  • 另请参阅此答案,其中以图形方式概述了XPath表达式的各个部分.

  • 这是一个很好的答案,但是对于记录来说,有一些不准确之处.(a)node-test""*"`的含义取决于轴:对于大多数轴,它选择元素节点,但是使用属性轴选择属性,并使用命名空间轴选择名称空间.(b)`@*`和`@ foo`不是节点测试,而是轴步骤,由两部分组成:一个轴(`@`,它是`attribute ::`的缩写)和一个节点测试(`*`或`foo`). (5认同)