<?php
/**
 * Tìm các phần tử HTML theo tên thẻ và thuộc tính.
 *
 * @param DOMDocument $doc Đối tượng DOMDocument đã tải HTML.
 * @param string $tag_name Tên thẻ HTML (mặc định là "*").
 * @param array $attributes Mảng thuộc tính và giá trị cần tìm.
 * @return DOMNodeList Danh sách các phần tử phù hợp.
 */
function find_elements_by_tag_and_attributes($doc, $tag_name = "*", $attributes = array()) {
    // Tạo đối tượng DOMXPath từ DOMDocument
    $xpath = new DOMXPath($doc);

    // Tạo query XPath với tên thẻ
    $xpath_query = "//" . $tag_name;

    // Nếu có thuộc tính cần tìm, thêm điều kiện vào query
    if (!empty($attributes)) {
        $conditions = array();
        foreach ($attributes as $attr => $value) {
            // Tìm kiếm giá trị gần đúng cho từng thuộc tính
            $conditions[] = "contains(@{$attr}, '{$value}')";
        }

        // Kết hợp các điều kiện thành một chuỗi XPath hoàn chỉnh
        $xpath_query .= "[" . implode(" and ", $conditions) . "]";
    }

    // Trả về danh sách các phần tử phù hợp với XPath query
    return $xpath->query($xpath_query);
}

Ví dụ Sử dụng

<?php
// Tạo đối tượng DOMDocument và tải nội dung HTML
$doc = new DOMDocument();
@$doc->loadHTML('<html><body><div id="dynamic" data-value="123">Content</div><div data-value="456">Another Content</div></body></html>');

// Tìm các phần tử div có thuộc tính 'data-value' chứa '123'
$elements = find_elements_by_tag_and_attributes($doc, 'div', array('data-value' => '123'));

foreach ($elements as $element) {
    echo "Thẻ: " . $element->nodeName . "<br>";
    echo "Thuộc tính data-value: " . $element->getAttribute('data-value') . "<br>";
    echo "Nội dung: " . $element->nodeValue . "<br>";
}

Giải thích

  1. Tạo đối tượng DOMXPath: Được sử dụng để thực hiện các truy vấn XPath trên đối tượng DOMDocument.
  2. Tạo truy vấn XPath: // được dùng để chọn tất cả các phần tử với tên thẻ chỉ định. Nếu có thuộc tính cần tìm, thêm điều kiện vào truy vấn.
  3. Truy vấn thuộc tính: contains(@attr, 'value') được dùng để tìm các phần tử mà thuộc tính chứa giá trị gần đúng.
  4. Trả về danh sách các phần tử: DOMXPath::query() trả về DOMNodeList, chứa tất cả các phần tử khớp với truy vấn XPath.

Hàm này cho phép bạn tìm kiếm các phần tử HTML trong tài liệu bằng cách sử dụng tên thẻ và thuộc tính tùy chỉnh, tương tự như trong ví dụ Python của bạn.