클래스 이름별 DOM 요소 가져오기

PHP DOM을 사용하고 있으며 DOM 노드 내에서 특정 클래스 이름을 가진 요소를 가져오려고 합니다.그 서브 엘리먼트를 입수하는 가장 좋은 방법은 무엇입니까?

업데이트: 사용되었습니다.MechanizePHP를 사용하기 쉽게 되어 있습니다.



질문에 대한 답변



업데이트: Xpath 버전*[@class~='my-class']css 셀렉터

그래서 하크레의 코멘트에 대한 아래의 코멘트를 듣고 궁금해서 뒤에 있는 코드를 조사했습니다.Zend_Dom_Query위의 셀렉터는 다음 xpath(테스트되지 않음)로 컴파일되어 있는 것 같습니다.

[contains(concat(' ', normalize-space(@class), ' '), ' my-class ')]

따라서 PHP는 다음과 같습니다.

$dom = new DomDocument(); $dom->load($filePath); $finder = new DomXPath($dom); $classname="my-class"; $nodes = $finder->query("//*[contains(concat(' ', normalize-space(@class), ' '), ' $classname ')]"); 

기본적으로, 여기서 우리가 하는 모든 일은,class단일 클래스도 공백으로 제한되고 전체 클래스 목록이 공백으로 제한되도록 속성을 지정합니다.그런 다음 찾고 있는 클래스를 공백으로 추가합니다.이 방법을 통해 델은 효과적인 방법으로 델이 찾고 있는 것은my-class .


xpath 셀렉터를 사용하시겠습니까?

$dom = new DomDocument(); $dom->load($filePath); $finder = new DomXPath($dom); $classname="my-class"; $nodes = $finder->query("//*[contains(@class, '$classname')]"); 

1가지 유형의 요소만 있는 경우 이 요소를 교환할 수 있습니다.*특정 타그네임과 함께.

매우 복잡한 셀렉터를 사용하여 이 작업을 많이 수행해야 하는 경우 가 CSS 셀렉터 구문(일명 jQuery)을 지원하는 것을 권장합니다.

$finder = new Zend_Dom_Query($html); $classname = 'my-class'; $nodes = $finder->query("*[class~="$classname"]"); 



zend를 사용하지 않고 클래스의 innerhtml을 가져오려면 다음을 사용할 수 있습니다.

$dom = new DomDocument(); $dom->load($filePath); $classname = 'main-article'; $finder = new DomXPath($dom); $nodes = $finder->query("//*[contains(concat(' ', normalize-space(@class), ' '), ' $classname ')]"); $tmp_dom = new DOMDocument();
foreach ($nodes as $node)
{
$tmp_dom->appendChild($tmp_dom->importNode($node,true));
} $innerHTML.=trim($tmp_dom->saveHTML());
echo $innerHTML; 



인정받는 방법이 더 낫다고 생각하지만, 이것도 효과가 있을 것 같아요.

function getElementByClass(&$parentNode, $tagName, $className, $offset = 0) {
$response = false;
$childNodeList = $parentNode->getElementsByTagName($tagName);
$tagCount = 0;
for ($i = 0; $i < $childNodeList->length; $i++) {
$temp = $childNodeList->item($i);
if (stripos($temp->getAttribute('class'), $className) !== false) {
 if ($tagCount == $offset) {

$response = $temp;

break;
 }

$tagCount++;
}
}
return $response; } 



다른 접근법도 있습니다.DomXPath또는Zend_Dom_Query.

dav의 원래 함수를 바탕으로 태그와 클래스가 파라미터와 일치하는 상위 노드의 모든 자식을 반환하는 다음 함수를 작성했습니다.

function getElementsByClass(&$parentNode, $tagName, $className) {
$nodes=array();
$childNodeList = $parentNode->getElementsByTagName($tagName);
for ($i = 0; $i < $childNodeList->length; $i++) {
$temp = $childNodeList->item($i);
if (stripos($temp->getAttribute('class'), $className) !== false) {
 $nodes[]=$temp;
}
}
return $nodes; } 

변수가 있다고 가정합니다.$html다음 HTML:

<html>
<body>
<div id="content_node">
<p class="a">I am in the content node.</p>
<p class="a">I am in the content node.</p>
<p class="a">I am in the content node.</p>
</div>
<div id="footer_node">
<p class="a">I am in the footer node.</p>
</div>
</body> </html> 

의 사용.getElementsByClass다음과 같이 심플합니다.

$dom = new DOMDocument('1.0', 'utf-8'); $dom->loadHTML($html); $content_node=$dom->getElementById("content_node");
$div_a_class_nodes=getElementsByClass($content_node, 'div', 'a');//will contain the three nodes under "content_node". 



DOMDocument 입력이 느리고 phpQuery에 메모리 누수 문제가 있습니다.사용 결과:

https://github.com/wasinger/htmlpagedom

클래스를 선택하려면:

include 'includes/simple_html_dom.php';
$doc = str_get_html($html); $href = $doc->find('.lastPage')[0]->href; 

이게 다른 사람에게도 도움이 됐으면 좋겠어요.