xml - read - XPath selecciona todos los elementos entre dos elementos específicos
xpath c# (4)
Tengo un siguiente 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>
Quiero seleccionar todos los p nodos después del primer elemento divisor hasta la siguiente aparición del elemento divisor. Intenté con seguir xpath:
//divider[1]/following-sibling::p[following::divider]
pero el problema es que selecciona todos los elementos p antes del último elemento divisor. No estoy seguro de cómo hacerlo usando xpath 1.
¿Qué hay de seleccionar todo p
teniendo exactamente un divider
elementos como preceding-sibling
?
//doc/p[preceding-sibling::divider[1] and not (preceding-sibling::divider[2])]
Creo que hay una solución mucho más simple y probablemente más rápida: quieres que todos los hermanos precedentes del segundo divisor que tienen al menos un divisor hermano anterior:
/doc/divider[2]/preceding-sibling::p[preceding-sibling::divider]
Se vuelve un poco más complejo, por supuesto, si quieres encontrar los parámetros entre el segundo y el tercer divisor: entonces quieres algo más parecido a la solución de Daniel Haley.
El mismo concepto que bytebuster, pero un xpath diferente:
/*/p[count(preceding-sibling::divider)=1]
Aquí hay una expresión general de XPath :
/*/divider[$k]
/following-sibling::p
[count(.|/*/divider[$k+1]/preceding-sibling::p)
=
count(/*/divider[$k+1]/preceding-sibling::p)
]
Si sustituye $k
por 1
entonces se seleccionan exactamente los p
nodos deseados.
si sustituyes $k
por 2
entonces todos los elementos p
entre el 2 ° y 3 ° divider
, ..., etc.
Explicación
Esta es una aplicación simple de la fórmula Kayessian XPath 1.0 para la intersección de conjuntos de nodos:
$ns1[count(.|$ns2) = count($ns2)]
selecciona todos los nodos que pertenecen a los conjuntos de nodos $ns1
y $ns2
.
En este caso específico, sustituimos $ns1
por:
/*/divider[$k]/following-sibling::p
y sustituimos $ns2
con:
/*/divider[$k+1]/preceding-sibling::p