【问题标题】:PHP call all XML nodes objects without mentioning child node namePHP 调用所有 XML 节点对象而不提及子节点名称
【发布时间】:2012-05-30 19:50:22
【问题描述】:
<Node name="node1">
  <x x="x"/>
  <x x="xxx"/>
</Node>

<Node name="node2">
  <x x="xx"/>
  <x x="xxxx"/>
</Node>

好的,这是一个 XML 示例:

我使用 simplexml_load_file 调用它的内容

如果我想调用一个特定的节点内容,它应该是:

$xml = simplexml_load_file('file.xml');
$contents = $xml->node1

并调用节点对象

$contents = $xml->node1->x

到目前为止看起来还不错, 问题是, 如何在不提及节点名称的情况下调用对象“x”

你注意到我在上面添加的示例有 2 个节点

要从中调用 x 我应该提到 nodename 然后是 x

我想从整个 XML 中调用所有“x”

这怎么可能?

【问题讨论】:

    标签: php xml loops


    【解决方案1】:

    SimpleXMLElement::xpath() 可以在您不必担心命名空间时解决问题。如果您确实有命名空间...您将需要 SimpleXMLElement::registerXPathNamespace()。

    <?php
    $xml = <<<EOT
    <?xml version="1.0" encoding="UTF-8" ?>
    <root>
    <Node name="node1">
      <x x="x"/>
      <x x="xxx"/>
    </Node>
    
    <Node name="node2">
      <x x="xx"/>
      <x x="xxxx"/>
    </Node>
    </root>
    EOT;
    
    // Original question
    $s = new SimpleXMLElement($xml);
    $r = $s->xpath('//Node/x');
    var_dump($r);
    
    // Something about names
    $r2 = $s->xpath('Node[@name]');
    $names = array();
    foreach($r2 as $elem){
      $names[] = "{$elem['name']}";
    }
    var_dump($names);
    
    // RoseWarad's answer (more efficient than "something about names")
    $r3 = $s->xpath('*/@name');
    var_dump($r3);
    
    ?>
    

    【讨论】:

    • 当您使用它时,这里有更多 xpath 可供使用:w3.org/TR/xpath/#path-abbrev
    • 如果我想选择所有没有 x 的节点名称怎么办?
    • 这将为您提供“name”属性等于“node2”的所有元素。此外,在这种情况下,您还将获得所有子节点(您可以自行决定忽略或处理)。 $r = $s->xpath('*[@name="node2"]');
    • 不,我的意思是,如何获取所有节点的名称,就像我对 x 所做的那样,所以它以 Node1、Node2 结尾,不包括 x 或其任何子节点
    • [误读您编辑的评论] 既然您更改了评论的问题...我不知道...获取所有节点,获取包括“x”在内的所有节点...做一个差异,然后你会有那些没有“x”的吗?这是(相对)昂贵/繁重的事情。我不知道 SimpleXMLElement::xpath 是否执行高级 xpath 2.0 表达式...而且我不知道必要的表达式...但也许这里的其他人会...
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-07-08
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多