[ ]
имеет более высокий приоритет, чем // (а "//" на самом деле является только сокращением, а не оператором). Это так, потому что согласно XPath 1.0 Spec ,
"// - это сокращение от / потомок-или-себя :: node () /"
и позже:
" ПРИМЕЧАНИЕ : путь местоположения // para 1 не означает то же самое, что путь местоположения / потомок :: para 1 . Последний выбирает первый элемент-потомок para; первый выбирает все элементы-потомки para, которые являются первыми para-потомками своих родителей. "
Следовательно, выражение XPath:
//element[@name='same'][2]
означает:
Выберите любой элемент в документе с именем «element», имеющий атрибут «name» со значением «same», и этот элемент является вторым таким потомком своего родителя.
То, что вы хотите, это :
(//element[@name='same'])[2]
Обратите внимание на скобки, которые переопределяют более высокий приоритет [].
Аналогично, последний, но один такой узел выбирается следующим выражением XPath:
(//element[@name='same'])[last()-1]
Наконец, необходимое предупреждение : Использование аббревиатуры "//" очень дорого, так как оно вызывает обход всего (под) дерева. Когда структура документа известна, рекомендуется использовать более конкретные конструкции (пути расположения).