首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >DOMDocument getElementsByTagNameNS

DOMDocument getElementsByTagNameNS
EN

Stack Overflow用户
提问于 2014-09-06 20:44:31
回答 2查看 289关注 0票数 0

我遇到了DOMDocument的一个问题::getElementsByTagNameNS,当我试图替换一个节点,或者我试图修改元素,一个是是,一个不是被修改的--这就是我的例子:

代码语言:javascript
复制
$xml = <<<EOD
<html xmlns:x="helloworld">
    <head>
        <title>ClasseAS - Home</title>
        <meta name="title" content="Hello World"/>
        <meta name="keywords" content="hello"/>
        <x:hello/>
        <x:hello/>
        <x:hello/>
        <x:hello/>
    </head>
</html>
EOD;

$DOMDocument = new DOMDocument("1.0","utf-8");

    $DOMDocument->loadXML($xml);
    foreach ($DOMDocument->getElementsByTagNameNS("helloworld","*") as $element){
        if($element->localName == "hello"){
            $else = $element;
            $fragment = $DOMDocument->createDocumentFragment();
            $fragment->appendXML("<div id=\"hello\"></div>");
            $else->parentNode->replaceChild($fragment,$else);
        }
    }

    $HTML = $DOMDocument->saveXML();
    echo "<pre>".htmlentities($HTML)."</pre>";
?>

我的错误在哪里?提前为我的糟糕英语道歉

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2014-09-06 22:06:21

DOMNodeList(由$DOMDocument->getElementsByTagNameNS("helloworld","*")返回)处于活动状态,当您替换节点时,将修改NodeList。

一些伪代码来澄清这种行为:

代码语言:javascript
复制
foreach(liveNodeList as $index => $element){
 //1st loop
          [node0, node1, node2, node3]
   //$index 0_^
   //$element is node0

 //2nd loop
          [node1, node2, node3]
   //$index 1_______^
   //$element is node2

 //3rd loop
          [node1, node3]
   //$index 2____________^
    //end of loop
}
  1. 在第一个循环中,$index0,NodeList包含4个元素。原始NodeList的第一项将被替换(并从NodeList中移除)
  2. 在第二个循环中,$index是1,但是NodeList现在只包含3个元素(第一个元素已被替换/删除)。$element现在是NodeList中具有$index 1的节点,但是循环必须再次用$index 0替换节点以获得所需的结果。原始Nodelist的第三项将被替换。
  3. 在第三个循环中,$index2,NodeList现在包含两个元素,$index点在NodeList的末尾。

可能的解决办法:

在NodeList的末尾启动节点替换:

代码语言:javascript
复制
for($i=$DOMDocument->getElementsByTagNameNS("helloworld","*")->length-1;
    $i>=0;--$i){
    $element=$DOMDocument->getElementsByTagNameNS("helloworld","*")->item($i);
    if($element->localName == "hello"){
        $fragment = $DOMDocument->createDocumentFragment();
        $fragment->appendXML("<div id=\"hello\"></div>");
        $element->parentNode->replaceChild($fragment,$element);
    }
}
票数 0
EN

Stack Overflow用户

发布于 2014-09-08 08:18:27

如果使用XPath选择元素,则可以在foreach循环中更可靠地操作它们:

代码语言:javascript
复制
$xpath = new DOMXPath($DOMDocument);
$xpath->registerNamespace('h', 'helloworld');

foreach ($xpath->query('//h:hello') as $element) {
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/25704576

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档