XPath: jak wybrać elementy na podstawie ich wartości?
Jestem nowy w używaniu XPath i może to być podstawowe pytanie. Prosimy o cierpliwość i pomoc w rozwiązaniu problemu. Mam taki plik XML:
<RootNode>
<FirstChild>
<Element attribute1="abc" attribute2="xyz">Data</Element>
<FirstChild>
</RootNode>
Mogę potwierdzić obecność znacznika <Element>
za pomocą:
//Element[@attribute1="abc" and @attribute2="xyz"]
Teraz chcę również sprawdzić wartość znacznika dla string "Data"
. W tym celu kazano mi użyć:
//Element[@attribute1="abc" and @attribute2="xyz" and Data]
Kiedy używam późniejszego wyrażenia, dostaję następujący błąd:
Komunikat o niepowodzeniu twierdzenia: brak dopasowanych węzłów
//Element[@attribute1="abc" and @attribute2="xyz" and Data]
Uprzejmie udziel mi porady, czy wyrażenie XPath, którego użyłem, jest poprawne. Jeśli nie, jakie będzie poprawne wyrażenie XPath?
2 answers
Warunek poniżej:
//Element[@attribute1="abc" and @attribute2="xyz" and Data]
Sprawdza istnienie danych elementu w elemencie, a nie dla danych wartości elementu.
Zamiast tego możesz użyć
//Element[@attribute1="abc" and @attribute2="xyz" and text()="Data"]
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-07-29 06:43:16
//Element[@attribute1="abc" and @attribute2="xyz" and .="Data"]
Powodem, dla którego dodaję tę odpowiedź jest to, że chcę wyjaśnić związek .
i text()
.
Pierwszą rzeczą jest użycie []
, istnieją tylko dwa typy danych:
-
*[number]
aby wybrać węzeł z zestawu węzłów -
*[bool]
aby odfiltrować node-set z node-set
W tym przypadku wartość jest obliczana na wartość logiczną przez funkcję boolean()
i istnieje reguła:
Filtry są zawsze oceniane w odniesieniu do kontekst.
Kiedy musisz porównać text()
lub .
z łańcuchem znaków "Data"
, najpierw używa funkcji string()
do przekształcenia ich w typ Łańcuchowy, a następnie otrzymuje wynik logiczny.
Istnieją dwie ważne zasady dotyczące string()
:
-
Funkcja
string()
konwertuje zestaw węzłów na łańcuch znaków, zwracając wartość pierwszego węzła w zestawie węzłów, co w niektórych przypadkach może przynieść nieoczekiwane wyniki.text()
jest ścieżką względną zwracającą zestaw węzłów zawiera cały węzeł tekstowy bieżącego węzła (węzeł kontekstowy), jak["Data"]
. Gdy jest oceniany przezstring(["Data"])
, zwróci pierwszy węzeł zestawu węzłów, więc otrzymasz "dane" tylko wtedy, gdy jest tylko jeden węzeł tekstowy w zestawie węzłów. -
Jeśli chcesz, aby funkcja
string()
łączyła cały tekst potomny, musisz przekazać pojedynczy węzeł zamiast zestawu węzłów.Na przykład, otrzymujemy node-set
['a', 'b']
, można przekazać tam węzeł nadrzędny dostring(parent)
, to zwróci'ab'
, a z przyczynystring(.)
w Twoim przypadku zwróci skonkatenowany łańcuch"Data"
.
Obie strony otrzymają ten sam wynik tylko wtedy, gdy jest węzeł tekstowy.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-08-14 21:28:20