Используя XPath, Как выбрать узел на основе его текстового содержимого и значения атрибута?
учитывая этот XML-код:
<DocText>
<WithQuads>
<Page pageNumber="3">
<Word>
July
<Quad>
<P1 X="84" Y="711.25" />
<P2 X="102.062" Y="711.25" />
<P3 X="102.062" Y="723.658" />
<P4 X="84.0" Y="723.658" />
</Quad>
</Word>
<Word>
</Word>
<Word>
30,
<Quad>
<P1 X="104.812" Y="711.25" />
<P2 X="118.562" Y="711.25" />
<P3 X="118.562" Y="723.658" />
<P4 X="104.812" Y="723.658" />
</Quad>
</Word>
</Page>
</WithQuads>
Я хотел бы найти узлы, которые имеют текст "июль" и атрибут Quad/P1/X больше 90. Таким образом, в этом случае он не должен возвращать никаких совпадений. Однако, если я использую GT ( > ) или LT (
так:
//Word[text()='July' and //P1[@X < 90]]
вернет true, как будет
//Word[text()='July' and //P1[@X > 90]]
как мне правильно ограничить это на P1@X атрибут?
кроме того, представьте, что у меня есть несколько элементов страницы, для разных номеров страниц. Как бы я дополнительно ограничить вышеуказанный поиск, чтобы найти узлы с text()='July', P1@X < 90
и на странице@pageNumber=3
?
2 ответа:
вообще я бы рассмотрел использование незафиксированного / / как плохой запах в XPath.
попробуйте это:-
/DocText/WithQuads/Page/Word[text()='July' and Quad/P1/@X > 90]
ваша проблема в том, что вы используете
//P1[@X < 90]
который начинается в начале документа и начинает охоту на любойP1
следовательно, это всегда будет верно. Точно так же//P1[@X > 90]
- это всегда правда.
помимо проблемы"//", этот XML-очень странное использование смешанного контента. Предикат
text()='July'
будет соответствовать элементу, если любой дочерний текстовый узел точно равен июлю, что не верно в вашем примере из-за окружающих пробелов. В зависимости от точного определения исходного XML, я бы пошел на[text()[normalize-space(.)='July'] and Quad/P1/@X > 90]