📅  最后修改于: 2020-11-09 14:29:13             🧑  作者: Mango
在BeautifulSoup中,需要处理两种主要的错误。这两个错误不是来自脚本,而是来自代码段的结构,因为BeautifulSoup API会引发错误。
两个主要错误如下-
当点表示法找不到当前HTML标签的同级标签时,会导致此错误。例如,您可能遇到此错误,因为缺少“ anchor tag”,cost-key遍历并需要定位标记时会抛出错误。
如果缺少必需的HTML标签属性,则会发生此错误。例如,如果我们在代码段中没有data-pid属性,则pid键将引发key-error。
为了避免在解析结果时出现上面列出的两个错误,将绕过该结果以确保未将格式错误的代码段插入数据库中-
except(AttributeError, KeyError) as er:
pass
每当我们发现要理解BeautifulSoup对我们的文档或HTML所做的任何困难时,只需将其传递给diagnostic()函数。通过将文档文件传递给diagnostic()函数,我们可以显示不同解析器列表如何处理文档。
下面是一个示例来演示如何使用diagnostic()函数-
from bs4.diagnose import diagnose
with open("20 Books.html",encoding="utf8") as fp:
data = fp.read()
diagnose(data)
解析错误主要有两种。当您将文档提供给BeautifulSoup时,可能会遇到HTMLParseError之类的异常。您还可能会得到意想不到的结果,其中BeautifulSoup解析树看起来与解析文档中的预期结果有很大差异。
没有任何解析错误是由于BeautifulSoup引起的。因为BeautifulSoup不包含任何解析器代码,所以由于使用了外部解析器(html5lib,lxml)。解决上述解析错误的一种方法是使用另一个解析器。
from HTMLParser import HTMLParser
try:
from HTMLParser import HTMLParseError
except ImportError, e:
# From python 3.5, HTMLParseError is removed. Since it can never be
# thrown in 3.5, we can just define our own class as a placeholder.
class HTMLParseError(Exception):
pass
Python内置的HTML解析器会导致两个最常见的解析错误:HTMLParser.HTMLParserError:格式错误的开始标记和HTMLParser.HTMLParserError:错误的结束标记,要解决此问题,主要是使用另一个解析器:lxml或html5lib。
另一种常见的意外行为类型是您找不到文档中已知的标签。但是,当您运行find_all()返回[]或find()返回None。
这可能是由于Python内置HTML解析器有时会跳过不了解的标签。
默认情况下,BeautifulSoup软件包将文档解析为HTML,但是,它非常易于使用,并且可以使用beautifulsoup4以非常优雅的方式处理格式错误的XML。
要将文档解析为XML,您需要具有lxml解析器,并且只需要将“ xml”作为第二个参数传递给Beautifulsoup构造函数-
soup = BeautifulSoup(markup, "lxml-xml")
要么
soup = BeautifulSoup(markup, "xml")
一个常见的XML解析错误是-
AttributeError: 'NoneType' object has no attribute 'attrib'
如果使用find()或findall()函数某些元素丢失或未定义,则可能会发生这种情况。
下面给出的是我们将在本节中讨论的其他一些解析错误-
除了上述解析错误外,您还可能遇到其他解析问题,例如环境问题,其中脚本可能在一个操作系统中运行,但在另一操作系统中无法运行,或者可能在一个虚拟环境中运行,但在另一虚拟环境中无法运行,或者可能无法运行虚拟环境之外。所有这些问题可能是因为两个环境具有可用的不同解析器库。
建议在当前的工作环境中了解或检查默认的解析器。您可以检查可用于当前工作环境的当前默认解析器,也可以将所需的解析器库作为第二个参数明确传递给BeautifulSoup构造函数。
由于HTML标记和属性不区分大小写,因此所有三个HTML解析器都将标记和属性名称转换为小写。但是,如果要保留大小写混合的标签和属性,则最好将文档解析为XML。
让我们看看下面的代码段-
soup = BeautifulSoup(response, "html.parser")
print (soup)
UnicodeEncodeError: 'charmap' codec can't encode character '\u011f'
上述问题可能是由于两种主要情况。您可能正在尝试打印出您的控制台不知道如何显示的unicode字符。其次,您尝试写入文件,并传入默认编码不支持的Unicode字符。
解决上述问题的一种方法是在使汤获得所需结果之前对响应文本/字符进行编码,如下所示:
responseTxt = response.text.encode('UTF-8')
这是由于相关标签未定义attr属性时访问tag [‘attr’]引起的。最常见的错误是:“ KeyError:’href’”和“ KeyError:’class’”。如果不确定是否定义了attr,请使用tag.get(’attr’)。
for item in soup.fetch('a'):
try:
if (item['href'].startswith('/') or "tutorialspoint" in item['href']):
(...)
except KeyError:
pass # or some other fallback action
您可能会遇到AttributeError,如下所示:
AttributeError: 'list' object has no attribute 'find_all'
发生上述错误的主要原因是,您期望find_all()返回单个标记或字符串。但是,soup.find_all返回一个Python元素列表。
您需要做的就是遍历列表并从这些元素中捕获数据。