我正在尝试匹配具有特定ID的div块。这是我的正则表达式代码:
<div\s+[^>]*\s*id\s*=\s*["|']content["|']\s*>[^/div]+
我希望正则表达式匹配整个div块。所以我把[^ / div] +放在我的正则表达式中,我假设它会匹配剩余的字符,直到它到达结尾但是它不能匹配直到结束,因为[^]表达式认为我不想要匹配任何&lt; / | d |我| v |取代。我想要的是将整个事情视为一个整体。放置一个[^()]也没有帮助..
所以请告诉我应该如何编码这个问题
<div id="content">
<noscript></noscript>
<a href="blabla.com">
<h1>
<a href="blablac.com">Blablabla</a>
</h1>
</div>
答案 0 :(得分:21)
答案 1 :(得分:3)
[^ / div] +会在到达任何这些字符时停止,这不是你想要的。由于 i ,它会在它到达时停止。
不幸的是,如果不首先了解HTML的内部结构,就无法做到你想要的。考虑一下:
<div id="content">
<div id="somethingelse">
</div>
</div>
即使你可以构建一个匹配到</div>
的正则表达式,你也无法构造一个匹配到正确</div>
的正则表达式。您需要进行更密集的解析。
答案 2 :(得分:0)
使用解析器,而不是正则表达式。
这是一个PHP示例:http://htmlparsing.com/php.html
答案 3 :(得分:0)
这篇文章很棒,是满足我需求的完美解决方案!
它甚至适用于simpleXML或DOMDocument失败的html代码!
有时您必须解析由您无法控制的 第三方 生成的HTML代码,并且 不尊重任何dtd ,所以这里是递归的正则表达式。
我只是对你的代码添加了一些修改,并将它与PHP preg_match_all函数一起使用。
在下面的示例中,我们将尝试正确匹配 div #content :
$content = <<<HTML
<div id="content">
<!-- tutu -->
<div id="something">
<div id="somethingElse">
<ul>
<li>lorem 1</li>
<li class="dfg" toto="titi">lorem 2</li>
<li class="dfg">lorem 3</li>
<li class="dfg">lorem 4</li>
<li class="dfg">lorem 5</li>
<li class="dfg">lorem 6</li>
</ul>
<br />
<div id="emptyStuff"></div>
</div>
</div>
<table>
<tr>
<td>cell 1</td>
<td>cell 2</td>
<td>cell 3</td>
<td>cell 4</td>
<td>cell 5</td>
<td>cell 6</td>
</tr>
<tr>
<td>cell 1</td>
<td>cell 2</td>
<td>cell 3</td>
<td>cell 4</td>
<td>cell 5</td>
<td>cell 6</td>
</tr>
</table>
</div>
HTML;
$pattern = '@# match nested tag
(?(DEFINE)
(?<comment> <!--.*?-->)
(?<cdata> <![CDATA[.*?]]>)
(?<empty> <\w+[^>]*?/>)
(?<inline> <(script|style)[^>]+>.*?</\g{-1}>)
(?<nested> <(\w+)[^>]*(?<!/)>(?&innerHTML)</\g{-1}>)
(?<unclosed> <\w+[^>]*(?<!/)>)
(?<text> [^<]+)
)
(?<outerHTML><(?<tagName>div)\s?(?<attributes>[^>]*?id\h*=\h*(?<quote>"|\')[^(?"e)\v>]*\bcontent\b[^(?"e)\v>]*(?"e)[^>]*)> # opening tag
(?<innerHTML>
(?: (?&comment) | (?&cdata) | (?&empty) | (?&inline) | (?&nested) | (?&unclosed) | (?&text) )*
)
</(?&tagName)>) # closing tag
@six';
preg_match_all($pattern, $content, $matches);
var_dump(array_intersect_key($matches, array(
'tagName' => 1,
'attributes' => 1,
'innerHTML' => 1,
'outerHTML' => 1
)));
以下是输出:
array(4) {
["outerHTML"]=>
array(1) {
[0]=>
string(639) "<div id="content">
<!-- tutu -->
<div id="something">
<div id="somethingElse">
<ul>
<li>lorem 1</li>
<li class="dfg" toto="titi">lorem 2</li>
<li class="dfg">lorem 3</li>
<li class="dfg">lorem 4</li>
<li class="dfg">lorem 5</li>
<li class="dfg">lorem 6</li>
</ul>
<br />
<div id="emptyStuff"></div>
</div>
</div>
<table>
<tr>
<td>cell 1</td>
<td>cell 2</td>
<td>cell 3</td>
<td>cell 4</td>
<td>cell 5</td>
<td>cell 6</td>
</tr>
<tr>
<td>cell 1</td>
<td>cell 2</td>
<td>cell 3</td>
<td>cell 4</td>
<td>cell 5</td>
<td>cell 6</td>
</tr>
</table>
</div>"
}
["tagName"]=>
array(1) {
[0]=>
string(3) "div"
}
["attributes"]=>
array(1) {
[0]=>
string(12) "id="content""
}
["innerHTML"]=>
array(1) {
[0]=>
string(615) "
<!-- tutu -->
<div id="something">
<div id="somethingElse">
<ul>
<li>lorem 1</li>
<li class="dfg" toto="titi">lorem 2</li>
<li class="dfg">lorem 3</li>
<li class="dfg">lorem 4</li>
<li class="dfg">lorem 5</li>
<li class="dfg">lorem 6</li>
</ul>
<br />
<div id="emptyStuff"></div>
</div>
</div>
<table>
<tr>
<td>cell 1</td>
<td>cell 2</td>
<td>cell 3</td>
<td>cell 4</td>
<td>cell 5</td>
<td>cell 6</td>
</tr>
<tr>
<td>cell 1</td>
<td>cell 2</td>
<td>cell 3</td>
<td>cell 4</td>
<td>cell 5</td>
<td>cell 6</td>
</tr>
</table>
"
}
}
我希望它会有所帮助!
答案 4 :(得分:-1)
<div id=content>.*?</div>
是你需要的 - 只要你没有嵌套的div。如果你有它们,请放弃并使用实际的XML解析器。
打开“dotall”选项(查看http://www.regular-expressions.info/dot.html,了解如何使用正则表达式进行操作)。
由您决定的细节。 : - )