Подтвердить что ты не робот

XPath выбирает все элементы между двумя конкретными элементами

У меня есть следующий xml:

<doc>
    <divider />
    <p>text</p>
    <p>text</p>
    <p>text</p>
    <p>text</p>
    <p>text</p>
    <divider />
    <p>text</p>
    <p>text</p>
    <divider />
    <p>text</p>
    <divider />
</doc>

Я хочу выбрать все p-узлы после первого элемента делителя до следующего появления элемента divider. Я пробовал со следующим xpath:

//divider[1]/following-sibling::p[following::divider]

но проблема в том, что он выбирает все элементы p перед последним элементом разделителя. Я не уверен, как это сделать, используя xpath 1.

4b9b3361

Ответ 1

Такое же понятие, как bytebuster, но другое xpath:

/*/p[count(preceding-sibling::divider)=1]

Ответ 2

Вот общее выражение XPath:

/*/divider[$k]
    /following-sibling::p
       [count(.|/*/divider[$k+1]/preceding-sibling::p)
       =
        count(/*/divider[$k+1]/preceding-sibling::p)
       ]

Если вы замените $k на 1, тогда будут выбраны именно нужные узлы p.

если вы замените $k на 2, тогда все p элементы между 2-м и 3-м divider,... и т.д.

Объяснение

Это простое применение формулы Kayessian XPath 1.0 для пересечения node -set:

$ns1[count(.|$ns2) = count($ns2)]

выбирает все узлы, принадлежащие к узлам узлов $ns1 и $ns2.

В этом конкретном случае подставляем $ns1:

/*/divider[$k]/following-sibling::p

и подставим $ns2:

/*/divider[$k+1]/preceding-sibling::p

Ответ 3

Как выбрать все p, имеющие ровно один элемент divider как preceding-sibling?

//doc/p[preceding-sibling::divider[1] and not (preceding-sibling::divider[2])]

Ответ 4

Я думаю, что существует гораздо более простое и, вероятно, более быстрое решение: вы хотите, чтобы все предыдущие братья и сестры второго разделителя имели по крайней мере один предшествующий разделитель для сестер:

/doc/divider[2]/preceding-sibling::p[preceding-sibling::divider]

Это немного сложнее, конечно, если вы хотите найти парас второго и третьего разделителей: тогда вам нужно что-то большее, как решение Daniel Haley.