我有以下要解析的html:
<h1 class="x">test</h1>
<p>some text <img src="x" /></p>
<h1 class="x1">test2</h1>
<p>some text </p>
<h1 class="2">test3</h1>
<p>some text <img src="x" /></p>
我可以将它解析为带有单个正则表达式的数组吗?
我试过
preg_match_all('#(<h1[^>]*?>)(.*?)(</h1>)(.*)#ism',$html,$arr);
只给我一个条目,因为正则表达式的最后一部分是贪婪的,而
preg_match_all('#(<h1[^>]*?>)(.*?)(</h1>)(.*?)#ism',$html,$arr);
它没有给我<h1>
之间的HTML,因为表达式并不贪婪。
如何在匹配贪婪之后制作零件,同时尽可能多地匹配?
补充意见:
答案 0 :(得分:4)
你需要某种形式的终结者。正则表达式无法猜测,直到您要匹配哪个部分。
在这种情况下可能是最后(.*?)
之后的先行断言:
(?=<h1|</body>|\z)#ims
答案 1 :(得分:1)
忽略有关正则表达式不合适的评论,因为它仍然是一个有趣的问题,有两种方法可以解决这个问题:贪婪和懒惰。
模式的各个部分是:
.*?(?=<h1|\z)
(?:[^<]+|<(?!h1))*
您可能熟悉the performance of greedy vs. lazy qualifiers in general,但这里的关键要简单得多。
如果你想要匹配的字符串完全由字符<
组成,那么懒惰和贪婪的模式将执行大致相同的操作,因为它们都必须检查每个匹配字符的断言。
然而,在HTML中你有比<
个字符更多的其他字符,所以贪婪的模式,不必检查其他字符,可以快几个数量级。
我承认懒惰模式更容易阅读,但我认为更好的性能是值得的,并且强烈建议您使用x
修饰符评论您的模式。