似乎在stackoverflow上的每个问题中,提问者使用regex从HTML中获取一些信息,将不可避免地有一个“答案”,说不要使用regex解析HTML。
为什么不呢?我知道有一些所谓的“真正的”HTML解析器,比如Beautiful Soup,我相信它们是强大而有用的,但如果您只是在做一些简单、快速或简单的事情,那么当一些正则表达式语句就可以很好地工作时,为什么要麻烦使用如此复杂的东西呢?
此外,是否只是因为我不理解正则表达式的某些基本原理,才使得它们在解析中成为一个糟糕的选择?
似乎在stackoverflow上的每个问题中,提问者使用regex从HTML中获取一些信息,将不可避免地有一个“答案”,说不要使用regex解析HTML。
为什么不呢?我知道有一些所谓的“真正的”HTML解析器,比如Beautiful Soup,我相信它们是强大而有用的,但如果您只是在做一些简单、快速或简单的事情,那么当一些正则表达式语句就可以很好地工作时,为什么要麻烦使用如此复杂的东西呢?
此外,是否只是因为我不理解正则表达式的某些基本原理,才使得它们在解析中成为一个糟糕的选择?
当前回答
问题是,大多数用户问的问题都与HTML和正则表达式有关,因为他们找不到自己的正则表达式。然后,必须考虑使用DOM或SAX解析器或类似的东西是否会更容易一些。它们是为处理类似xml的文档结构而优化和构造的。
当然,有些问题可以用正则表达式轻松解决。但重点在于容易。
如果您只想找到所有看起来像http://.../的url,那么使用regexp是没问题的。但是如果你想要找到a- element中所有具有'mylink'类的url,你可能最好使用合适的解析器。
其他回答
对于快速´n´dirty regexp就可以了。但是要知道的基本问题是,不可能构造一个正确解析HTML的regexp。
原因是regexp不能处理任意嵌套的表达式。参见正则表达式能否用于匹配嵌套模式?
正则表达式对于HTML这样的语言来说还不够强大。当然,有一些例子可以使用正则表达式。但通常不适合进行解析。
就解析而言,正则表达式在“词法分析”(lexer)阶段很有用,在这个阶段,输入被分解成标记。它在实际的“构建解析树”阶段用处不大。
对于HTML解析器,我希望它只接受格式良好的HTML,而这需要正则表达式所不能做到的功能(它们不能“计数”并确保给定数量的开始元素与相同数量的结束元素相平衡)。
Actually, HTML parsing with regex is perfectly possible in PHP. You just have to parse the whole string backwards using strrpos to find < and repeat the regex from there using ungreedy specifiers each time to get over nested tags. Not fancy and terribly slow on large things, but I used it for my own personal template editor for my website. I wasn't actually parsing HTML, but a few custom tags I made for querying database entries to display tables of data (my <#if()> tag could highlight special entries this way). I wasn't prepared to go for an XML parser on just a couple of self created tags (with very non-XML data within them) here and there.
所以,即使这个问题已经死了,它仍然会出现在谷歌搜索中。我读了它,并认为“接受挑战”,并完成了修复我的简单代码,而不需要替换所有东西。决定给有类似理由的人提供不同的意见。最后一个答案是4小时前发布的,所以这仍然是一个热门话题。
(来自http://htmlparsing.com/regexes)
假设您有一个HTML文件,您试图从中提取url < img >标签。
<img src="http://example.com/whatever.jpg">
所以你可以用Perl写一个这样的正则表达式:
if ( $html =~ /<img src="(.+)"/ ) {
$url = $1;
}
在本例中,$url确实包含 http://example.com/whatever.jpg。但是当 你会得到这样的HTML:
<img src='http://example.com/whatever.jpg'>
or
<img src=http://example.com/whatever.jpg>
or
<img border=0 src="http://example.com/whatever.jpg">
or
<img
src="http://example.com/whatever.jpg">
否则你就会得到假阳性
<!-- // commented out
<img src="http://example.com/outdated.png">
-->
它看起来很简单,对于一个单一的、不变的文件来说可能很简单,但是对于任意HTML数据,正则表达式只会让你将来头疼。