2017-01-07 7 views
1

Я пытаюсь проанализировать XML-файл с информацией о некоторых пользователях. Что-то вроде этогоКак найти элемент в определенном контексте с помощью DOMXPath в php?

users.xml

<?xml version="1.0" encoding="UTF-8"?> 
<users> 
    <user> 
     <name>Alexander</name> 
     <email>[email protected]</email> 
    </user> 
    <user> 
     <name>Tyler</name> 
     <email>[email protected]</email> 
    </user> 
</users> 

Я использую DOMXpath для извлечения всех пользователей внутри этого XML, и все это поле. В XML-файле, у меня есть 15 пользователей и когда поиск по всем полям около одного пользователя в этом коде

$username = $xpath->query ('//email', $users->item(0)); 

Я получил 15 длину, вместо 1. Я имею в виду query ищет во всех XML вместо того, чтобы искать для фактический пользователь. Что я делаю неправильно?

xml_query.php

$xml = new DOMDocument(); 
$xml->loadXML($xml_content); 
$xpath = new DOMXPath($xml); 

$users = $xpath->query('//user'); 
var_dump($users->item(0)); 
$username = $xpath->query ('//email', $users->item(0)); 

var_dump($username); 
+0

'DOMXPath' аргумент должен быть типа' DOMDocument' не XML файл. – Mohammad

+0

Я пропустил две полосы в моем коде, 'DOMXPath' имеет' DOMDocument' в конструкторе @Mohammad –

+0

Удалить '//' из '// email' –

ответ

1

Поскольку //email выбрать все элементы документа, но вы должны выбрать элементы в текущем контексте. Удалите // из выражения запроса.

$username = $xpath->query ('email', $users->item(0)); 

См приводит к demo

+0

Теперь с' email' я получаю 'length' 0. –

1

косая черта (/) в начале пути доступа делает его относительно узла документа. Контекстный узел будет проигнорирован. Если за ним следует другая косая черта, она использует ось потомка. //email не подходит для /descendant::email. Ось по умолчанию - child.

$xml = <<<'XML' 
<?xml version="1.0" encoding="UTF-8"?> 
<users> 
    <user> 
     <name>Alexander</name> 
     <email>[email protected]</email> 
    </user> 
    <user> 
     <name>Tyler</name> 
     <email>[email protected]</email> 
    </user> 
</users> 
XML; 

$document = new DOMDocument(); 
$document->loadXml($xml); 
$xpath = new DOMXpath($document); 
foreach ($xpath->evaluate('//user') as $user) { 
    var_dump($xpath->evaluate('string(email)', $user)); 
} 

Выход:

string(18) "[email protected]" 
string(14) "[email protected]" 

DOMXpath::evaluate() может возвращать списки узлов или скаляры в зависимости от выражения. Это позволяет вам накладывать узлы на строку непосредственно в выражении Xpath.

выражение

Xpath может содержать условия, чтобы выводить электронную почту на позиции, которую вы могли бы сделать что-то вроде:

foreach ($xpath->evaluate('//user[2]') as $user) { 
    var_dump($xpath->evaluate('string(email)', $user)); 
} 

Выход:

string(14) "[email protected]" 

 Смежные вопросы

  • Нет связанных вопросов^_^