首页 > 代码库 > python学习之----异常处理小示例

python学习之----异常处理小示例

网络是十分复杂的。网页数据格式不友好,网站服务器宕机,目标数据的标签找不到,都

是很麻烦的事情。网络数据采集最痛苦的遭遇之一,就是爬虫运行的时候你洗洗睡了,梦

想着明天一早数据就都会采集好放在数据库里,结果第二天醒来,你看到的却是一个因某

种数据格式异常导致运行错误的爬虫,在前一天当你不再盯着屏幕去睡觉之后,没过一会

儿爬虫就不再运行了。那个时候,你可能想骂发明互联网(以及那些奇葩的网络数据格

式)的人,但是你真正应该斥责的人是你自己,为什么一开始不估计可能会出现的异常!

 

html = urlopen("http://www.pythonscraping.com/pages/page1.html")

 

这行代码主要可能会发生两种异常:

? 网页在服务器上不存在(或者获取页面的时候出现错误)

? 服务器不存在

第一种异常发生时,程序会返回HTTP 错误。HTTP 错误可能是“404 Page Not Found”“500

Internal Server Error”等。所有类似情形,urlopen 函数都会抛出“HTTPError”异常。我们

可以用下面的方式处理这种异常:

try:

html = urlopen("http://www.pythonscraping.com/pages/page1.html")

except HTTPError as e:

print(e)

 

# 返回空值,中断程序,或者执行另一个方案

else:

# 程序继续。注意:如果你已经在上面异常捕捉那一段代码里返回或中断(break),

# 那么就不需要使用else语句了,这段代码也不会执行

如果程序返回HTTP 错误代码,程序就会显示错误内容,不再执行else 语句后面的代码。

如果服务器不存在(就是说链接http://www.pythonscraping.com/ 打不开,或者是URL 链接

写错了),urlopen 会返回一个None 对象。这个对象与其他编程语言中的null 类似。我们

可以增加一个判断语句检测返回的html 是不是None:

if html is None:

print("URL is not found")

else:

# 程序继续

 

当然,即使网页已经从服务器成功获取,如果网页上的内容并非完全是我们期望的那样,

仍然可能会出现异常。每当你调用BeautifulSoup 对象里的一个标签时,增加一个检查条件

保证标签确实存在是很聪明的做法。如果你想要调用的标签不存在,BeautifulSoup 就会返

初见网络爬虫 | 9

回None 对象。不过,如果再调用这个None 对象下面的子标签,就会发生AttributeError

错误。

下面这行代码(nonExistentTag 是虚拟的标签,BeautifulSoup 对象里实际没有)

print(bsObj.nonExistentTag)

会返回一个None 对象。处理和检查这个对象是十分必要的。如果你不检查,直接调用这个

None 对象的子标签,麻烦就来了。如下所示。

print(bsObj.nonExistentTag.someTag)

这时就会返回一个异常:

AttributeError: ‘NoneType‘ object has no attribute ‘someTag‘

那么我们怎么才能避免这两种情形的异常呢?最简单的方式就是对两种情形进行检查:

try:

badContent = bsObj.nonExistingTag.anotherTag

except AttributeError as e:

print("Tag was not found")

else:

if badContent == None:

print ("Tag was not found")

else:

print(badContent)

 

初看这些检查与错误处理的代码会觉得有点儿累赘,但是,我们可以重新简单组织一下代

码,让它变得不那么难写(更重要的是,不那么难读)。例如,下面的代码是上面爬虫的

另一种写法:

from urllib.request import urlopen

from urllib.error import HTTPError

from bs4 import BeautifulSoup

def getTitle(url):

try:

html = urlopen(url)

except HTTPError as e:

return None

try:

bsObj = BeautifulSoup(html.read())

title = bsObj.body.h1

except AttributeError as e:

return None

return title

title = getTitle("http://www.pythonscraping.com/pages/page1.html")

if title == None:

print("Title could not be found")

else:

print(title)

 

 

在这个例子中,我们创建了一个getTitle 函数,可以返回网页的标题,如果获取网页

的时候遇到问题就返回一个None 对象。在getTitle 函数里面,我们像前面那样检查了

HTTPError,然后把两行BeautifulSoup 代码封装在一个try 语句里面。这两行中的任何一

行有问题,AttributeError 都可能被抛出(如果服务器不存在,html 就是一个None 对象,

html.read() 就会抛出AttributeError)。其实,我们可以在try 语句里面放任意多行代码,

或者放一个在任意位置都可以抛出AttributeError 的函数。

python学习之----异常处理小示例