在Python中解析HTML - lxml还是BeautifulSoup?各自适合什么用途?
从我了解到的情况来看,Python中主要有两个处理HTML的库,一个是lxml,另一个是BeautifulSoup。我在做一个项目的时候选择了BeautifulSoup,但其实没有特别的理由,只是觉得它的语法比较容易学和理解。不过我看到很多人更喜欢lxml,而且听说lxml的速度更快。
所以我在想,这两者各自的优点是什么呢?什么时候我应该使用lxml,什么时候又更适合用BeautifulSoup?还有没有其他值得考虑的库呢?
7 个回答
简单来说,lxml
是一个非常快速的 HTML 和 XML 解析工具,它的质量很高。此外,它还包含一个 soupparser
模块,可以使用 BeautifulSoup 的功能。BeautifulSoup
是一个个人项目,旨在帮助你快速从格式不太好的 HTML 或 XML 中提取数据,节省时间。
lxml 文档提到这两种解析器各有优缺点。因此,lxml
提供了一个 soupparser
,让你可以在两者之间切换。引用一下,
BeautifulSoup 使用不同的解析方法。它并不是真正的 HTML 解析器,而是通过正则表达式来处理混乱的标签。因此,在某些情况下它更宽容,但在其他情况下表现不佳。通常情况下,lxml/libxml2 能更好地解析和修复损坏的 HTML,但 BeautifulSoup 对编码检测的支持更强。哪个解析器更好,实际上取决于输入内容。
最后他们说,
使用这个解析器的缺点是,它比 lxml 的 HTML 解析器慢得多。所以如果性能很重要,你可能只想在特定情况下将 soupparser 作为备用。
如果我理解得没错,这意味着 soup 解析器更强大——它可以通过正则表达式处理格式不正确的标签“汤”,而 lxml
则更直接,只是解析内容并构建一个树状结构,正如你所期待的那样。我想这也适用于 BeautifulSoup
本身,而不仅仅是 lxml
的 soupparser
。
他们还展示了如何在快速解析 lxml
的同时,利用 BeautifulSoup
的编码检测:
>>> from BeautifulSoup import UnicodeDammit
>>> def decode_html(html_string):
... converted = UnicodeDammit(html_string, isHTML=True)
... if not converted.unicode:
... raise UnicodeDecodeError(
... "Failed to detect encoding, tried [%s]",
... ', '.join(converted.triedEncodings))
... # print converted.originalEncoding
... return converted.unicode
>>> root = lxml.html.fromstring(decode_html(tag_soup))
(同一来源:http://lxml.de/elementsoup.html).
根据 BeautifulSoup
创始人的话,
就这样!祝你玩得开心!我写 Beautiful Soup 是为了节省大家的时间。一旦你习惯了,你应该能在几分钟内从设计不佳的网站中提取数据。如果你有任何意见、遇到问题,或者想让我知道你使用 Beautiful Soup 的项目,请给我发邮件。
--Leonard
引用自 Beautiful Soup 文档。
我希望这现在很清楚。Soup 是一个出色的个人项目,旨在帮助你从设计不佳的网站中提取数据,节省时间。目标是让你现在就能完成工作,而不一定是为了长期节省时间,当然也不是为了优化你软件的性能。
此外,来自 lxml 网站,
lxml 在 Python 包索引上已经被下载超过两百万次,并且在许多软件包分发中也可以直接获得,例如 Linux 或 MacOS-X。
还有,来自 为什么选择 lxml?,
C 库 libxml2 和 libxslt 有巨大的优势:... 符合标准... 功能齐全... 快速,快速!快!... lxml 是 libxml2 和 libxslt 的新 Python 绑定...
Pyquery
是一个让 Python 可以使用 jQuery 选择器的工具(它的底层是用 lxml 实现的)。
http://pypi.python.org/pypi/pyquery
这个工具非常棒,我现在不再使用其他的了。
首先,BeautifulSoup这个工具现在已经不再积极维护了,作者甚至推荐使用其他工具,比如lxml。
引用一下链接页面上的内容:
Beautiful Soup的3.1.0版本在处理真实的HTML时表现得比3.0.8版本差很多。最常见的问题包括错误处理标签、出现“错误的开始标签”错误和“错误的结束标签”错误。这个页面解释了发生了什么,问题将如何解决,以及你现在可以做些什么。
这个页面最初是在2009年3月写的。从那以后,3.2系列已经发布,取代了3.1系列,而4.x系列的开发也已经开始。这个页面将保留以供历史参考。
总结一下
建议使用3.2.0版本。