python网络爬虫Word文档下载推荐.docx
《python网络爬虫Word文档下载推荐.docx》由会员分享,可在线阅读,更多相关《python网络爬虫Word文档下载推荐.docx(66页珍藏版)》请在冰点文库上搜索。
URL是URI的一个子集。
它是UniformResourceLocator的缩写,译为“统一资源定位符”。
通俗地说,URL是Internet上描述信息资源的字符串,主要用在各种WWW客户程序和服务器程序上。
采用URL可以用一种统一的格式来描述各种信息资源,包括文件、服务器的地址和目录等。
URL的格式由三部分组成:
①第一部分是协议(或称为服务方式)。
②第二部分是存有该资源的主机IP地址(有时也包括端口号)。
③第三部分是主机资源的具体地址,如目录和文件名等。
第一部分和第二部分用“:
//”符号隔开,
第二部分和第三部分用“/”符号隔开。
第一部分和第二部分是不可缺少的,第三部分有时可以省略。
下面来看看两个URL的小例子。
1.HTTP协议的URL示例:
使用超级文本传输协议HTTP,提供超级文本信息服务的资源。
例:
其计算机域名为。
超级文本文件(文件类型为.html)是在目录/channel下的welcome.htm。
这是中国人民日报的一台计算机。
超级文本文件(文件类型为.html)是在目录/talk下的talk1.htm。
这是瑞得聊天室的地址,可由此进入瑞得聊天室的第1室。
2.文件的URL
用URL表示文件时,服务器方式用file表示,后面要有主机IP地址、文件的存取路径(即目录)和文件名等信息。
有时可以省略目录和文件名,但“/”符号不能省略。
file:
//
上面这个URL代表存放在主机上的pub/files/目录下的一个文件,文件名是foobar.txt。
代表主机上的目录/pub。
代表主机的根目录。
爬虫最主要的处理对象就是URL,它根据URL地址取得所需要的文件内容,然后对它进行进一步的处理。
因此,准确地理解URL对理解网络爬虫至关重要。
利用urllib2通过指定的URL抓取网页内容
所谓网页抓取,就是把URL地址中指定的网络资源从网络流中读取出来,保存到本地。
类似于使用程序模拟IE浏览器的功能,把URL作为HTTP请求的内容发送到服务器端,然后读取服务器端的响应资源。
在Python中,我们使用urllib2这个组件来抓取网页。
urllib2是Python的一个获取URLs(UniformResourceLocators)的组件。
它以urlopen函数的形式提供了一个非常简单的接口。
最简单的urllib2的应用代码只需要四行。
我们新建一个文件urllib2_test01.py来感受一下urllib2的作用:
[python]
viewplaincopy
1.import
urllib2
2.response
=
urllib2.urlopen('
3.html
response.read()
4.print
html
按下F5可以看到运行的结果:
我们可以打开XX主页,右击,选择查看源代码(火狐OR谷歌浏览器均可),会发现也是完全一样的内容。
也就是说,上面这四行代码将我们访问XX时浏览器收到的代码们全部打印了出来。
这就是一个最简单的urllib2的例子。
除了"
http:
"
,URL同样可以使用"
ftp:
,"
等等来替代。
HTTP是基于请求和应答机制的:
客户端提出请求,服务端提供应答。
urllib2用一个Request对象来映射你提出的HTTP请求。
在它最简单的使用形式中你将用你要请求的地址创建一个Request对象,
通过调用urlopen并传入Request对象,将返回一个相关请求response对象,
这个应答对象如同一个文件对象,所以你可以在Response中调用.read()。
我们新建一个文件urllib2_test02.py来感受一下:
2.req
urllib2.Request('
'
)
3.response
urllib2.urlopen(req)
4.the_page
5.print
the_page
可以看到输出的内容和test01是一样的。
urllib2使用相同的接口处理所有的URL头。
例如你可以像下面那样创建一个ftp请求。
1.req
在HTTP请求时,允许你做额外的两件事。
1.发送data表单数据
这个内容相信做过Web端的都不会陌生,
有时候你希望发送一些数据到URL(通常URL与CGI[通用网关接口]脚本,或其他WEB应用程序挂接)。
在HTTP中,这个经常使用熟知的POST请求发送。
这个通常在你提交一个HTML表单时由你的浏览器来做。
并不是所有的POSTs都来源于表单,你能够使用POST提交任意的数据到你自己的程序。
一般的HTML表单,data需要编码成标准形式。
然后做为data参数传到Request对象。
编码工作使用urllib的函数而非urllib2。
我们新建一个文件urllib2_test03.py来感受一下:
urllib
2.import
3.
4.url
5.
6.values
{'
name'
:
WHY'
7.
location'
SDU'
8.
language'
Python'
}
9.
10.data
urllib.urlencode(values)
#
编码工作
11.req
urllib2.Request(url,
data)
发送请求同时传data表单
12.response
#接受反馈的信息
13.the_page
#读取反馈的内容
如果没有传送data参数,urllib2使用GET方式的请求。
GET和POST请求的不同之处是POST请求通常有"
副作用"
,
它们会由于某种途径改变系统状态(例如提交成堆垃圾到你的门口)。
Data同样可以通过在Get请求的URL本身上面编码来传送。
4.data
{}
6.data['
]
7.data['
8.data['
10.url_values
urllib.urlencode(data)
11.print
url_values
12.
13.name=Somebody+Here&
language=Python&
location=Northampton
14.url
15.full_url
url
+
?
16.
17.data
urllib2.open(full_url)
这样就实现了Data数据的Get传送。
2.设置Headers到http请求
有一些站点不喜欢被程序(非人为访问)访问,或者发送不同版本的内容到不同的浏览器。
默认的urllib2把自己作为“Python-urllib/x.y”(x和y是Python主版本和次版本号,例如Python-urllib/2.7),
这个身份可能会让站点迷惑,或者干脆不工作。
浏览器确认自己身份是通过User-Agent头,当你创建了一个请求对象,你可以给他一个包含头数据的字典。
下面的例子发送跟上面一样的内容,但把自身模拟成InternetExplorer。
6.user_agent
Mozilla/4.0
(compatible;
MSIE
5.5;
Windows
NT)'
7.values
10.
11.headers
{
User-Agent'
user_agent
12.data
13.req
data,
headers)
14.response
15.the_page
异常的处理和HTTP状态码的分类
先来说一说HTTP的异常处理问题。
当urlopen不能够处理一个response时,产生urlError。
不过通常的PythonAPIs异常如ValueError,TypeError等也会同时产生。
HTTPError是urlError的子类,通常在特定HTTPURLs中产生。
1.URLError
通常,URLError在没有网络连接(没有路由到特定服务器),或者服务器不存在的情况下产生。
这种情况下,异常同样会带有"
reason"
属性,它是一个tuple(可以理解为不可变的数组),
包含了一个错误号和一个错误信息。
我们建一个urllib2_test06.py来感受一下异常的处理:
2.
3.req
4.
5.try:
6.
7.except
urllib2.URLError,
e:
print
e.reason
按下F5,可以看到打印出来的内容是:
[Errno11001]getaddrinfofailed
也就是说,错误号是11001,内容是getaddrinfofailed
2.HTTPError
服务器上每一个HTTP应答对象response包含一个数字"
状态码"
。
有时状态码指出服务器无法完成请求。
默认的处理器会为你处理一部分这种应答。
例如:
假如response是一个"
重定向"
,需要客户端从别的地址获取文档,urllib2将为你处理。
其他不能处理的,urlopen会产生一个HTTPError。
典型的错误包含"
404"
(页面无法找到),"
403"
(请求禁止),和"
401"
(带验证请求)。
HTTP状态码表示HTTP协议所返回的响应的状态。
比如客户端向服务器发送请求,如果成功地获得请求的资源,则返回的状态码为200,表示响应成功。
如果请求的资源不存在,则通常返回404错误。
HTTP状态码通常分为5种类型,分别以1~5五个数字开头,由3位整数组成:
------------------------------------------------------------------------------------------------
200:
请求成功
处理方式:
获得响应的内容,进行处理
201:
请求完成,结果是创建了新资源。
新创建资源的URI可在响应的实体中得到
爬虫中不会遇到
202:
请求被接受,但处理尚未完成
阻塞等待
204:
服务器端已经实现了请求,但是没有返回新的信息。
如果客户是用户代理,则无须为此更新自身的文档视图。
丢弃
300:
该状态码不被HTTP/1.0的应用程序直接使用,只是作为3XX类型回应的默认解释。
存在多个可用的被请求资源。
若程序中能够处理,则进行进一步处理,如果程序中不能处理,则丢弃
301:
请求到的资源都会分配一个永久的URL,这样就可以在将来通过该URL来访问此资源
重定向到分配的URL
302:
请求到的资源在一个不同的URL处临时保存
重定向到临时的URL
304请求的资源未更新
丢弃
400非法请求
401未授权
403禁止
404没有找到
5XX回应代码以“5”开头的状态码表示服务器端发现自己出现错误,不能继续执行请求
HTTPError实例产生后会有一个整型'
code'
属性,是服务器发送的相关错误号。
ErrorCodes错误码
因为默认的处理器处理了重定向(300以外号码),并且100-299范围的号码指示成功,所以你只能看到400-599的错误号码。
BaseHTTPServer.BaseHTTPRequestHandler.response是一个很有用的应答号码字典,显示了HTTP协议使用的所有的应答号。
当一个错误号产生后,服务器返回一个HTTP错误号,和一个错误页面。
你可以使用HTTPError实例作为页面返回的应答对象response。
这表示和错误属性一样,它同样包含了read,geturl,和info方法。
我们建一个urllib2_test07.py来感受一下:
4.try:
e.code
#print
e.read()
按下F5可以看见输出了404的错误码,也就说没有找到这个页面。
3.Wrapping
所以如果你想为HTTPError或URLError做准备,将有两个基本的办法。
推荐使用第二种。
我们建一个urllib2_test08.py来示范一下第一种异常处理的方案:
1.from
import
Request,
urlopen,
URLError,
HTTPError
Request('
response
urlopen(req)
9.except
HTTPError,
11.
The
server
couldn\'
t
fulfill
the
request.'
13.
Error
code:
14.
15.except
17.
We
failed
to
reach
a
server.'
18.
19.
Reason:
20.
21.else:
22.
No
exception
was
raised.'
23.
everything
is
fine
和其他语言相似,try之后捕获异常并且将其内容打印出来。
这里要注意的一点,exceptHTTPError必须在第一个,否则exceptURLError将同样接受到HTTPError
因为HTTPError是URLError的子类,如果URLError在前面它会捕捉到所有的URLError(包括HTTPError
)。
我们建一个urllib2_test09.py来示范一下第二种异常处理的方案:
if
hasattr(e,
reason'
):
15.
elif
21.
23.else:
24.
25.
Opener与Handler的介绍和实例应用
在开始后面的内容之前,先来解释一下urllib2中的两个个方法:
infoandgeturl
urlopen返回的应答对象response(或者HTTPError实例)有两个很有用的方法info()和geturl()
1.geturl():
这个返回获取的真实的URL,这个很有用,因为urlopen(或者opener对象使用的)或许会有重定向。
获取的URL或许跟请求URL不同。
以人人中的一个超级链接为例,
我们建一个urllib2_test10.py来比较一下原始URL和重定向的链接:
4.old_url
5.req
Request(old_url)
6.response
7.print
Old
old_url
8.print
Real
response.geturl()
运行之后可以看到真正的链接指向的网址:
2.info():