简单的Python爬虫

爬虫的定义:一段自动抓取互联网信息的程序,从互联网上抓取对于我们有价值的信息。Python 爬虫架构主要由五个部分组成,分别是调度器、URL管理器、网页下载器、网页解析器、应用程序(爬取的有价值数据)。

  • 调度器:相当于一台电脑的CPU,主要负责调度URL管理器、下载器、解析器之间的协调工作。
  • URL管理器:包括待爬取的URL地址和已爬取的URL地址,防止重复抓取URL和循环抓取URL,实现URL管理器主要用三种方式,通过内存、数据库、缓存数据库来实现。
  • 网页下载器:通过传入一个URL地址来下载网页,将网页转换成一个字符串,网页下载器有urllib2(Python官方基础模块)包括需要登录、代理、和cookie,requests(第三方包)
  • 网页解析器:将一个网页字符串进行解析。网页解析器在简单情况下用正则表达式匹配,除此还有html.parser(Python自带的)、beautifulsoup(第三方插件,可以使用Python自带的html.parser进行解析,也可以使用lxml进行解析,相对于其他几种来说要强大一些)、lxml(第三方插件,可以解析 xml 和 HTML),html.parser 和 beautifulsoup 以及 lxml 都是以 DOM 树的方式进行解析的。
  • 应用程序:就是从网页中提取的有用数据组成的一个应用。

使用urllib2 打开网页并返回一个对象

1
2
3
4
5
6
7
8
url=' '
params = urllib.urlencode({'loc':'108288','day_type':'weekend','type':'exhibition'})#构建请求参数
page = urllib.request.urlopen(url) #打开网页并返回一个对象
html = page.read() #直接获得网页的源代码
print page
print response.headers
print response.status_code.getcode() #获取网页内容的长度
return html
1
2
request = urllib.request.Request(url, headers=headers)
response = urllib.request.urlopen(request)

使用request

1
2
3
response = requests.get(url,params=params)
print response.headers
print response.status_code

两种做对比:
1)构建参数:在构建请求参数时,第一种需要将请求参数使用urllib库的urlencode方法进行编码预处理

2)请求方法:发送get请求时,第一种使用的urllib库的urlopen方法打开一个url地址,而第二种直接使用requests库的get方法,与http请求方式是对应的

3)请求数据:第一种按照url格式去拼接一个url字符串,第二种按顺序将get请求的url和参数写好就可以了

4)处理响应:第一种处理消息头部、响应状态码和响应正文时分别使用.info()、.getcode()、.read()方法,第二种使用.headers、.status_code、.text方法

5)连接方式:看一下返回数据的头信息的“connection”,使用urllib库时,”connection”:”close”,说明每次请求结束关掉socket通道,而使用requests库使用了urllib3,多次请求重复使用一个socket,”connection”:”keep-alive”,说明多次请求使用一个连接,消耗更少的资源

6)编码方式:requests库的编码方式Accept-Encoding更全,

爬取图片

1
2
3
for img in imglist:
urllib.request.urlretrieve(url+img, '%s.jpg' %index)
index += 1
1
2
3
4
with open(filePath,'wb')as f:
request = urllib.request.Request(url, headers=headers)
response = urllib.request.urlopen(request)
f.write(response.read())

urlretrieve()方法直接将远程数据下载到本地。

urlretrieve(url, filename=None, reporthook=None, data=None)
参数filename指定了保存本地路径(如果参数未指定,urllib会生成一个临时文件保存数据。)
参数reporthook是一个回调函数,当连接上服务器、以及相应的数据块传输完毕时会触发该回调,我们可以利用这个回调函数来显示当前的下载进度。
参数data指post导服务器的数据,该方法返回一个包含两个元素的(filename, headers) 元组,filename 表示保存到本地的路径,header表示服务器的响应头

爬取视频

1
2
3
4
5
6
r = requests.get(url, headers=head, stream=True)

with open('./downLoad.mp4', "wb") as mp4:
for chunk in r.iter_content(chunk_size=1024 * 1024):
if chunk:
mp4.write(chunk)
1
2
3
4
5
6
7
8
9
10
chunk_size = 1024	  # 单次请求最大值
content_size = int(r.headers['content-length']) # 内容体总大小
print '下载开始'
with open(path, "wb") as f:
n = 1
for chunk in r.iter_content(chunk_size=chunk_size):
loaded = n*1024.0/content_size
f.write(chunk)
print '已下载{0:%}'.format(loaded)
n += 1

获取请求的原始响应可以用:Response.raw、Response.iter_content
普通情况可以用 r.raw,在初始请求中设置 stream=True,来获取服务器的原始套接字响应
当流下载时,用Response.iter_content更方便些。
requests.get(url)默认是下载在内存中的,下载完成才存到硬盘上
可以用Response.iter_content 边下载边存硬盘

-------------本文结束感谢您的阅读-------------
/*
*/