Python多进程爬虫 提高运行效率 爬虫开发 分布式爬虫

鳄鱼君

发表文章数:642

Vieu四代商业主题

高扩展、安全、稳定、响应式布局多功能模板。

¥69 现在购买
首页 » Python » Python多进程爬虫 提高运行效率 爬虫开发 分布式爬虫

在看这篇文章之前,确保你已经掌握了requests库正则表达式,这时候你可能需要写一个爬虫代码,但是你写的爬虫代码此时只有一个进程、一个线程,这叫做单线程爬虫。单线程爬虫每次只能访问一个页面,不能充分利用计算机的带宽。一个页面有几百KB,爬虫在爬取一个页面的时候,多出来的网速和从发起请求到得到源代码中间的时间都被浪费掉了。

如果可以让爬虫同时访问10个页面,就相当于爬取速度也提高了10倍。那么就需要使用多线程技术了。这里你可能还需要了解一点,Python这门语言在设计的时候,有一个全局解释器锁GIL(Global Interpreter Lock),这导致Python的多线程都是伪线程,本质上还是一个线程,但是这个线程每个事情只做几毫秒,几毫秒之后就保存现场,换做其它事情,几毫秒之后再做其它事情…微观上的单线程,在宏观上就像同时在做几件事。这种I/O(Input/Output,输入/输出)密集型操作上影响不大,但是在CPU计算密集型的操作上面,由于只能使用CPU的一个核,就会对性能产生非常大的影响。所以设计计算密集型的程序,就需要使用多进程,Python的多进程不受GIL的影响。

爬虫属于I/O密集型的程序,所以我们使用多线程可以大大提高爬虫效率.

Python多进程库

multiprocessing本身是Python的进程库,用来处理与多进程相关的操作。但是由于进程与进程之间不能共享内存和堆栈资源,而且启动新的进程开销也比线程的大得多,因此使用多线程来爬取比使用多进程有更多的优势。multiprocessing下面有一个dummy模块。它可以让Python的线程使用multiprocessing的各种方法。

dummy模块有一个Pool类,就是线程池,这个线程池有一个map()方法,可以让线程池里面的所有线程都同时(同时是在我们看来)执行一个函数。

from multiprocessing.dummy import Pool

def fun(num): #定义一个函数计算平方
    return num*num
pool=Pool(4) #初始化4个进程池
data=[x for x in range(10)]
result=pool.map(fun,data) #map()方法的第一个参数为函数名,第二个参数是一个列表
print('计算0-9的平方分别为:%s'% result)

map()方法第一个参数为函数的名字,不能加上()。第二个参数是个可迭代对象(元组,集合或者字典),这个可迭代对象里面的每一个元素都会被fun函数接收作为参数。

开发多进程爬虫

前面说过,爬虫属于I/O密集型的操作,特别是在请求网页源代码的时候,如果使用单线程来开发,那么会浪费大量的时间来等待网页返回,所以把多线程技术应用到爬虫中,可以大大提高爬虫的效率。可以通过测试来比较单线程爬虫多线程爬虫的性能差异。这里分别访问淘宝官网100次,计算总时间:

import requests
import time
from multiprocessing.dummy import Pool

def get_taobao(url):
    requests.get(url)
star_time=time.time()
for i in range(100):
    get_taobao('http://www.taobao.com')
end_time=time.time()
print('单线程下运行时间为:%s'% (end_time-star_time))


data=[]
strat=time.time()
for a in range(100):
    data.append('http://www.taobao.com')
pool=Pool(5)
pool.map(get_taobao,data)
end=time.time()
print('多线程下运行时间:%s'% (end-strat))

从运行结果我们可以简单比较一下,5个线程池的运行时间大约为单线程的五分之一左右,这里受电脑配置和网速影响,测试结果可能不同。但是在微观上还是串行的。线程池的大小就需要合理掌控,设置过大,线程的切换导致的开销可能会抵消多线程带来性能和速度上的提升,这就需要你自己尝试了,可以把请求淘宝的次数增加,线程池也增加,试试,找到一个合适的数据。

爬虫常见搜索算法

深度优先搜索

这里需要通过一个简单的列子来说明。比方说淘宝网站中的分类商品,你需要爬取所有的商品信息,从首页开始,商品有几个大的分类,比如男装、数码、箱包、食品,每个大分类下面又有很多的小分类,比如男装下面有棉衣、休闲长裤、萝卜裤..。每个小分类下面则是很多的商品了。那么深度优先搜索的路线为“首页→男装→棉衣、萝卜裤、休闲长裤……→数码→笔记本电脑、平板电脑、无人机…→箱包–双肩背包、旅行箱、小方包…”。也就是说,先爬取首页下男装的所有商品,再爬取数码的所有商品,接着爬取箱包的所有商品….

广度优先搜索

那么广度优先搜索的路线为“首页→男装→数码→箱包→男装下的所有商品→数码下的商品→箱包下的所有商品”。也就是说,首先爬取每个大分类的信息,然后从第1个大分类中爬取所有的商品信息,爬完了第1个大分类,再爬第2个大分类,直到所有大分类下面的商品信息都搞定了,再爬第一个大分类下的小分类……

爬虫搜索算法的选择

在爬虫开发的过程中,应该选择深度优先还是广度优先呢?这就需要根据被爬取的数据来进行选择了。如果爬取的信息具有时效性,就是受时间因素的影响,这时候就需要采用广度优先搜索;那么如果需要爬取的数据具有实时舆情,你就需要采用深度优先搜索当然,这两种搜索算法并非非此即彼,需要根据实际情况灵活选择,很多时候也能够同时使用。

未经允许不得转载:作者:鳄鱼君, 转载或复制请以 超链接形式 并注明出处 鳄鱼君
原文地址:《Python多进程爬虫 提高运行效率 爬虫开发 分布式爬虫》 发布于2019-12-18

分享到:
赞(0) 赏杯咖啡

评论 抢沙发

8 + 1 =


文章对你有帮助可赏作者一杯咖啡

支付宝扫一扫打赏

微信扫一扫打赏

Vieu4.6主题
专业打造轻量级个人企业风格博客主题!专注于前端开发,全站响应式布局自适应模板。
切换注册

登录

忘记密码 ?

您也可以使用第三方帐号快捷登录

Q Q 登 录
微 博 登 录
切换登录

注册