选择所有节点,直到一个特定的给定节点/标签

问题描述:

考虑下面的标记。在这种情况下,我以下节点之后我:选择所有节点,直到一个特定的给定节点/标签

<dd>A</dd> 
<dd>B</dd> 
<dd>C</dd> 

我想下面的XPath代码,但预期它不工作。

xpath("//div[@id='about']/dl/dt[contains(text(),'Names')]/following-sibling::dd[not(following-sibling::dt)]/text()") 

有关如何解决它的任何想法?

非常感谢。

更新:更简单的解决

。在你的情况的一个先决条件,那就是锚项目始终是第一个前置兄弟具有一定的财产。正因为如此,这里的写作以下复杂表达式的一个更简单的方法:

/div/dl/dd[preceding-sibling::dt[1][. = 'Names']] 

换句话说:

  • 选择任何dd
  • 具有第一前置兄弟dt(前面的兄弟轴向后计数)
  • 其本身具有“名称”的值

从oXygen的以下屏幕截图可以看出,它选择您想要选择的节点(如果将“名称”更改为“状态”或“另一个字段”,它将在下一个dt之前选择仅以下几个节点也)。

screenshot from oXygen of selected nodes

原本复杂的解决方案(留下供参考)

这是XPath 2.0中更容易,但是让我们假设你只能使用XPath 1.0。诀窍在于计算来自锚元素(其中包含“名称”的元素)中前一个兄弟元素的数量,并忽略任何错误数量的元素(即,当我们跨过<dt>Status</dt>时,前面的兄弟元素数量增加) 。

对于XPath 1.0中,除去(::)之间的意见(XPath中,空白是无关紧要的,你可以把它的可读性多的XPath,但在1.0,评论是不可能的)

/div/dl/dd 

    (: any dd having a dt before it with "Names" :) 
    [preceding-sibling::dt[. = 'Names']] 

    (: count the preceding siblings up to dt with "Names", add one to include 'self' :) 
    [count(preceding-sibling::dt[. = 'Names']/preceding-sibling::dt) + 1 
    = 

    (: compare with count of all preceding siblings :) 
    count(preceding-sibling::dt)] 

由于一行:

/div/dl/dd[preceding-sibling::dt[. = 'Names']][count(preceding-sibling::dt[. = 'Names']/preceding-sibling::dt) + 1 = count(preceding-sibling::dt)] 
+0

感谢您的解释。试图了解它:) –

+0

@安德烈,很高兴我能有一定的帮助! :) – Abel

如何:

//dd[preceding-sibling::dt[contains(., 'Names')]][following-sibling::dt] 
+0

没有。这将返回所有''

以下'
名称
':'
一个
Ç
'。 –
+0

我用'oXygen'编辑器执行这个表达式,它给了我预期的结果。 '

'不应该出现在结果中。这个元素没有后面的兄弟'
'。 – Kachna
+0

哦,我明白了。你是对的。但我已经更新了标记在原来的问题,以满足另一种情况,其中有'

另一场
'。现在您的代码将在''返回
,对不对? –