Bardziej ogólne powiązane rozwiązania XPath, CSS, DOM i Selenium można znaleźć w dokumencie XPath, CSS, DOM i Selenium: Kamień z Rosetty . W szczególności odpowiedź można znaleźć w identyfikatorze i nazwie przedmiotu .
Terence Xie,
Odpowiedzi:
472
Ten selektor powinien działać, ale będzie bardziej wydajny, jeśli zastąpisz go odpowiednim znacznikiem:
//*[contains(@class, 'Test')]
Lub, ponieważ wiemy, że poszukiwany element to div:
//div[contains(@class, 'Test')]
Ale ponieważ będzie to również pasować do przypadków takich jak class="Testvalue"lub class="newTest", wersja @ Tomalak podana w komentarzach jest lepsza :
//div[contains(concat(' ', @class, ' '), ' Test ')]
Jeśli chcesz być naprawdę pewien, że będzie pasował poprawnie, możesz również użyć funkcji normalizacji spacji, aby usunąć zbłąkane białe znaki wokół nazwy klasy (jak wspomniano w @Terry):
//div[contains(concat(' ', normalize-space(@class), ' '), ' Test ')]
Zauważ, że we wszystkich tych wersjach * należy najlepiej zastąpić dowolną nazwą elementu, który chcesz dopasować, chyba że chcesz wyszukać każdy element w dokumencie pod kątem danego warunku.
@meder: Bardziej jak //div[contains(concat(' ', @class, ' '), ' Test ')]- Twoi pojawią się również częściowe mecze.
Tomalak
5
Dlaczego nie zrobisz // div [@ class = 'Test']
Jessica,
11
Ponieważ klasy mogą zawierać więcej niż jedną wartość
meder omuraliev
8
Dziwi mnie, że xpath nie ma skrótu / bardziej wydajnego sposobu na zlokalizowanie tokena na liście tokenów oddzielonych spacjami. Coś w późniejszych wersjach Xpath?
thomasrutter
1
@ thomasrutter, dlaczego niespodzianka - to tylko język stworzony dla XML, a nie bardziej szczegółowy HTML, i kto powiedziałby, że swobodnie jest używać list rozdzielonych spacjami jako dowolnej wartości węzła w XML. Rozwiązanie Tomalaka jest bardzo realne.
bitoolean
152
Najłatwiejszy sposób ..
//div[@class="Test"]
Zakładając, że chcesz znaleźć <div class="Test">zgodnie z opisem.
Powyższa składnia jest dużo łatwiejsza w użyciu i mniej podatna na błędy. PAMIĘTAJ, że musisz mieć PODWÓJNE CYTATY wokół klasy, aby szukać. Polecam korzystanie z wymienionych powyżej. // div [@ class = "Test"]
FlyingV
Czy to działa w przypadkach, w których div [class = 'Test'] leży na głębszym poziomie?
Jake0x32
1
@ Jake0x32, to dlatego, że używa //nie tylko /.
Solomon Ucko
7
Czy pasuje również do `<div class =" Test some-other-class ">?
Jugal Thakkar
11
@JugalThakkar Nie, nie ma. Wymaga dokładnego dopasowania, ale możesz spróbować // div [zawiera (@class, „Test”)].
Olli Puljula
29
Tylko właściwy sposób to zrobić z XPath:
//div[contains(concat(" ", normalize-space(@class), " "), " Test ")]
Funkcja normalize-spaceusuwa wiodące i końcowe białe znaki, a także zastępuje ciąg znaków białych znaków pojedynczą spacją.
Uwaga
Jeśli nie potrzebujesz wielu z tych zapytań Xpath, możesz użyć biblioteki, która konwertuje selektory CSS na XPath, ponieważ selektory CSS są zwykle o wiele łatwiejsze zarówno do odczytu, jak i zapisu niż zapytania XPath. Na przykład w tym przypadku można użyć obu div[class~="Test"]i div.Testuzyskać ten sam wynik.
Przykro mi, że o tym wspomniałem z tamtych czasów, ale co powiesz concat(' ', normalize-space(@class), ' ')na wszystkie rodzaje białych znaków?
Terry
Ze względu na ciekawość - dlaczego //div[contains(concat(' ', @class, ' '), ' Test ')]/chidnie wybiera dzieci?
Fusion
@Fusion, jeśli opublikujesz to jako pytanie, możesz uzyskać odpowiedź.
bitoolean
@bitoolean bycie Kapitanem Cbvious jest obecnie trudne
Fusion
@Fusion Chciałem tylko pomóc. XPath nie jest językiem obsługującym HTML. Jest bardziej ogólny, tylko w języku XML. Nie mam w tym żadnego doświadczenia, ale myślę, że zakładasz, że możesz po prostu wstawić identyfikator zamiast tagu. Musisz wybrać wartość atrybutu „id”. Musisz więc pomyśleć o dokumencie HTML jako XML. Dyskusje poza tematem nie pomagają jednak znaleźć rozwiązań.
bitoolean
1
Pomocną funkcję można uzyskać z poprzednich odpowiedzi:
Odpowiedzi:
Ten selektor powinien działać, ale będzie bardziej wydajny, jeśli zastąpisz go odpowiednim znacznikiem:
Lub, ponieważ wiemy, że poszukiwany element to
div
:Ale ponieważ będzie to również pasować do przypadków takich jak
class="Testvalue"
lubclass="newTest"
, wersja @ Tomalak podana w komentarzach jest lepsza :Jeśli chcesz być naprawdę pewien, że będzie pasował poprawnie, możesz również użyć funkcji normalizacji spacji, aby usunąć zbłąkane białe znaki wokół nazwy klasy (jak wspomniano w @Terry):
Zauważ, że we wszystkich tych wersjach * należy najlepiej zastąpić dowolną nazwą elementu, który chcesz dopasować, chyba że chcesz wyszukać każdy element w dokumencie pod kątem danego warunku.
źródło
//div[contains(concat(' ', @class, ' '), ' Test ')]
- Twoi pojawią się również częściowe mecze.Najłatwiejszy sposób ..
Zakładając, że chcesz znaleźć
<div class="Test">
zgodnie z opisem.źródło
//
nie tylko/
.Tylko właściwy sposób to zrobić z XPath:
Funkcja
normalize-space
usuwa wiodące i końcowe białe znaki, a także zastępuje ciąg znaków białych znaków pojedynczą spacją.Uwaga
Jeśli nie potrzebujesz wielu z tych zapytań Xpath, możesz użyć biblioteki, która konwertuje selektory CSS na XPath, ponieważ selektory CSS są zwykle o wiele łatwiejsze zarówno do odczytu, jak i zapisu niż zapytania XPath. Na przykład w tym przypadku można użyć obu
div[class~="Test"]
idiv.Test
uzyskać ten sam wynik.Niektóre biblioteki, które udało mi się znaleźć:
źródło
Podaję to tylko jako odpowiedź, jak dawno temu Tomalak jako komentarz do odpowiedzi medera
źródło
concat(' ', normalize-space(@class), ' ')
na wszystkie rodzaje białych znaków?//div[contains(concat(' ', @class, ' '), ' Test ')]/chid
nie wybiera dzieci?Pomocną funkcję można uzyskać z poprzednich odpowiedzi:
Następnie po prostu połącz wywołanie funkcji z zapytaniem.
źródło
Dopasuj do jednej klasy, która ma spacje.
źródło
możesz znaleźć elementy takie jak ten przykład (wszystkie elementy css)
źródło