簡體   English   中英

使用正則表達式模式重復捕獲組

[英]Repeating capture group with a regex pattern

我正在嘗試從網站上獲取產品列表,包括各個產品代碼。 產品代碼是5位代碼,元素的復雜程度從

<p>Part Number: 67001</p>

<p>Part Number: 50545 &ndash; 450g Cartridge 50525 - 2.5kg Tub 50520 - 20kg Pail 50555 - 55kg Drum 50575 *Indent - 175kg Drum</p>

不幸的是,五位數字模式遍及整個網頁,所以我不能只使用/\\d{5}/

我使用的是正則表達式,該正則表達式僅提取“零件號”元素中的5位數字,而不提取網頁的其余部分。

類似於: /\\<p\\>Part\\s*Number\\:\\s*((\\d{5}) repeat this capture group n times)\\<\\/p\\>/

我知道我可以做到這一點,可以分階段分解頁面並逐個應用一個正則表達式。 例如

第一階段/\\<p\\>Part\\s*Number\\:\\s*.*?\\<\\/p\\>/
第二階段/\\d{5}/

但是有可能以一種正則表達式模式執行嗎?

我現在比一年前要聰明得多,所以我完全抹掉了最初的建議。 嘗試解析有效​​的html時,最好/最可靠的方法是使用dom解析器。 XPath使節點/元素搜尋超級容易。 一旦取消了不包含Part Number關鍵字的<p>標記的資格,則正則表達式模式仍然是一種合適的工具。

代碼:( 演示

$html = <<<HTML
<p>Zip Code: 99501</p>
<p>Part Number: 67001</p>
<p>Part Number: 98765 - 10000kg capacity</p>
<p>Some dummy/interfering text. Part Number: 12345</p>
<p>Zip Codes: 99501, 99524 , 85001 and 72201</p>
<p>Part Number: 50545 &ndash; 450g Cartridge 50525 - 2.5kg Tub 50520 - 20kg Pail 50555 - 55kg Drum 50575 *Indent - 175kg Drum</p>
HTML;

$partnos = [];

$dom = new DOMDocument;
$dom->loadHTML($html);
$xpath = new DOMXPath($dom);
foreach ($xpath->query("//p[starts-with(., 'Part Number: ')]") as $node) {
    // echo "Qualifying text: {$node->nodeValue}\n";
    if (preg_match_all('~\b\d{5}\b~', $node->nodeValue, $matches)) {
        $partnos = array_merge($partnos, $matches[0]); //or array_push($partnos, ...$matches[0]);
    }
}
var_export($partnos);

輸出:

array (
  0 => '67001',
  1 => '98765',
  2 => '50545',
  3 => '50525',
  4 => '50520',
  5 => '50555',
  6 => '50575',
)

xpath查詢說:

//p                  #find p tags at any level/position in the dom
[starts-with(.       #with a substring at the start of the node's text
, 'Part Number: ')]  #that literally matches "Part Number: "

正則表達式模式使用單詞邊界元字符\\b )來區分零件編號和非零件編號。 如果由於問題中未包含某些數據而需要調整模式,請告知我們,我們將提供進一步的指導。

最終,我調情了一個純正則表達式解決方案,該解決方案將\\G包含在“ Part Number:或之前的匹配之后以“繼續”匹配,但是這種類型的模式很難概念化,並且dom解析器再次是更穩定的工具與正則表達式處理有效的html時。

如果我正確理解了您的問題,則應該可以執行以下操作:

Part\\sNumber:\\s(\\d{5})

假設您的字符串包含所有的Part Number ,如下所示:

<p>Part Number: 67001</p>

<p>Part Number: 50545 &ndash; 450g Cartridge 50525 - 2.5kg Tub 50520 - 20kg Pail 50555 - 55kg Drum 50575 *Indent - 175kg Drum</p>

<p>Part Number: 23425 - 55kg Drum 50575 *Indent - 175kg Drum</p>

<p>Part Number: 52232</p>

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM