Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/php/285.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
如何获取PHP中所有html元素的列表?_Php_Html_Dom - Fatal编程技术网

如何获取PHP中所有html元素的列表?

如何获取PHP中所有html元素的列表?,php,html,dom,Php,Html,Dom,根据的文档,我可以使用“*”参数调用函数,并从一些HTML代码中获取所有HTML元素的列表 但是,使用以下代码: <?php $dom = new DOMDocument(); $dom->loadHTML("<html><body><div>hello</div><div>bye</div></body></html>"); $nodes = $dom->getElem

根据的文档,我可以使用
“*”
参数调用函数,并从一些HTML代码中获取所有HTML元素的列表

但是,使用以下代码:

<?php
  $dom = new DOMDocument();
  $dom->loadHTML("<html><body><div>hello</div><div>bye</div></body></html>");
  $nodes = $dom->getElementsByTagName("*");

  foreach ($nodes as $node) {
    $new_text= new DOMText($node->textContent."MODIFIED");

    $node->removeChild($node->firstChild);
    $node->appendChild($new_text);
  }
  $content = $dom->saveHTML();
  echo $content;
?>

我只得到一个元素的列表,上面代码的执行结果是:

<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN" "http://www.w3.org/TR/REC-html40/loose.dtd">
<html>hellobyeMODIFIED</html>

Hellobye修改
虽然我希望这样:

<html><body><div>helloMODIFIED</div><div>byeMODIFIED</div></body></html>
helloMODIFIEDbyeMODIFIED
DOMDocument::getElementsByTagName
方法不应该返回HTML代码中尽可能多的HTML元素的列表吗


注意:我需要显式地创建DOMText实例,因为我需要它在PHP5.4中工作
DOMNode::textContent
仅可从PHP5.6进行写入
DOMDocument::getElementsByTagName
方法实际返回所有标记,如果第一个参数是
“*”
。但是,在第一次迭代时,您的代码将
标记(包括所有子节点)替换为文本节点

迭代节点,仅修改
nodeType
属性等于
XML\u TEXT\u NODE
的节点:

$nodes = $dom->getElementsByTagName('*');

foreach ($nodes as $node) {
  for ($child = $node->firstChild; $child; $child = $child->nextSibling) {
    if (! ($child->nodeType === XML_TEXT_NODE && trim($child->textContent))) {
      continue;
    }

    // The textContent is writable since PHP 5.6.1
    if (PHP_VERSION_ID >= 50601) {
      $child->textContent .= 'MODIFIED';
      continue;
    }

    // For older versions, create DOMText explicitly
    $text = new DOMText($child->textContent . 'MODIFIED');
    try {
      if ($child->parentNode->replaceChild($text, $child))
        $child = $text;
    } catch (Exception $e) {
      trigger_error("Failed to modify text '$child->textContent': "
        . $e->getMessage(), E_USER_WARNING);
    }
  }
}

echo $dom->saveHTML();
注意,对于PHP版本5.6.1及更高版本,您不需要显式创建
DOMText
实例,因为
DOMNode::textContent
属性可用于读写。因此,您可以通过为该属性指定字符串值来简单地修改文本。仅确保该节点除了
XML\u TEXT\u节点
之外没有其他子节点

上面的代码检查
trim($child->textContent)
是否为空,因为文档可能包含额外的空格字符(包括换行符),例如:


文本

如果第一个参数是
“*”
,则
DOMDocument::getElementsByTagName方法实际上返回所有标记。但是,在第一次迭代时,您的代码将
标记(包括所有子节点)替换为文本节点

迭代节点,仅修改
nodeType
属性等于
XML\u TEXT\u NODE
的节点:

$nodes = $dom->getElementsByTagName('*');

foreach ($nodes as $node) {
  for ($child = $node->firstChild; $child; $child = $child->nextSibling) {
    if (! ($child->nodeType === XML_TEXT_NODE && trim($child->textContent))) {
      continue;
    }

    // The textContent is writable since PHP 5.6.1
    if (PHP_VERSION_ID >= 50601) {
      $child->textContent .= 'MODIFIED';
      continue;
    }

    // For older versions, create DOMText explicitly
    $text = new DOMText($child->textContent . 'MODIFIED');
    try {
      if ($child->parentNode->replaceChild($text, $child))
        $child = $text;
    } catch (Exception $e) {
      trigger_error("Failed to modify text '$child->textContent': "
        . $e->getMessage(), E_USER_WARNING);
    }
  }
}

echo $dom->saveHTML();
注意,对于PHP版本5.6.1及更高版本,您不需要显式创建
DOMText
实例,因为
DOMNode::textContent
属性可用于读写。因此,您可以通过为该属性指定字符串值来简单地修改文本。仅确保该节点除了
XML\u TEXT\u节点
之外没有其他子节点

上面的代码检查
trim($child->textContent)
是否为空,因为文档可能包含额外的空格字符(包括换行符),例如:


文本
试试这个:-

foreach($dom->getElementsByTagName('*') as $element ){

}
试试这个:-

foreach($dom->getElementsByTagName('*') as $element ){

}

此函数“DOMDocument::getElementsByTagName”返回包含所有元素的类DOMNodeList的新实例

而且效果很好:


它输出文档的所有标记

可能您需要smth,如:

<?php


    $dom = new DOMDocument();
      $dom->loadHTML("<html><body><div>hello</div><div>bye</div></body></html>");
      $nodes = $dom->getElementsByTagName("*");

      foreach ($nodes as $node) {
          if ($node->tagName=='div'){
            $node->nodeValue .= "new content";
          }
      }

      $content = $dom->saveHTML();
      echo htmlspecialchars($content);

?>

此函数“DOMDocument::getElementsByTagName”返回包含所有元素的类DOMNodeList的新实例

而且效果很好:


它输出文档的所有标记

可能您需要smth,如:

<?php


    $dom = new DOMDocument();
      $dom->loadHTML("<html><body><div>hello</div><div>bye</div></body></html>");
      $nodes = $dom->getElementsByTagName("*");

      foreach ($nodes as $node) {
          if ($node->tagName=='div'){
            $node->nodeValue .= "new content";
          }
      }

      $content = $dom->saveHTML();
      echo htmlspecialchars($content);

?>


您的元素具有相同的标记名…@Alexis,是的,但是如果我通过getElementsByTagName(“div”)更改getElementsByTagName(*”),那么我会得到我想要的结果,并且元素仍然具有相同的标记名。@MarcosFernandez,不清楚您到底想要实现什么。是否要修改所有文本节点?还是要修改具有文本节点的叶子(最后一个标记)的所有文本节点?例如,如何修改此序列
textabcdef
?@Ruslan Osmanov我需要处理页面中的所有文本元素。它们不一定会被修改,但我必须检查它们。在您的示例中,如果所有这些文本元素都应该修改,那么结果将是:
textModifiedABC修改dDefModified
您提到您需要它在PHP5.4中工作,即使您知道5.6中的功能可能会有所帮助。升级有多困难?实际上,5.4和5.6之间没有明显的向后兼容性问题,因此升级应该非常容易。此外,5.4不再受支持,因此您确实应该考虑升级。您的元素具有相同的标记名…@Alexis,是的,但是如果我通过getElementsByTagName(“div”)更改getElementsByTagName(*),那么我会得到我想要的结果,并且元素仍然具有相同的标记名。@MarcosFernandez,现在还不清楚你到底想要实现什么。是否要修改所有文本节点?还是要修改具有文本节点的叶子(最后一个标记)的所有文本节点?例如,如何修改此序列
textabcdef
?@Ruslan Osmanov我需要处理页面中的所有文本元素。它们不一定会被修改,但我必须检查它们。在您的示例中,如果所有这些文本元素都应该修改,那么结果将是:
textModifiedABC修改dDefModified
您提到您需要它在PHP5.4中工作,即使您知道5.6中的功能可能会有所帮助。升级有多困难?实际上,5.4和5.6之间没有明显的向后兼容性问题,因此升级应该非常容易。另外,5.4不再受支持,所以你真的应该考虑升级了。谢谢,差不多了!只有一件事:我确实需要显式地创建DOMText实例,因为我需要它在PHP5.4中工作
DOMNode::textContent
只能从PHP5.6上进行编写。我仍然无法在5.4上完成此操作。非常感谢!。我被孩子->父母节点的事情缠住了。谢谢你的解释。节省了很多时间!谢谢,差不多了!只有一件事:我确实需要显式地创建DOMText实例,因为我需要这样做