python多进程加多线程爬虫_Python的多线程和多进程——从一个爬虫任务谈起 !...

本文的目的是解释为何在Python中须要多线程和多处理,什么时候使用多线程和多进程,以及它们能怎样提升咱们程序的性能。数据库

假设咱们的量化模型须要从多个网站爬取一些数据,咱们将要对比用单线程和多线程的方法有何性能上的差异。数组

1,单线程,单进程网络

在单线程、单进程中,咱们将用for循环读取一个url列表。多线程

如您所见,咱们只是使用for循环一个接一个地遍历url并读取响应。咱们可使用IPython的%%time函数对消耗的时间进行统计,这个读取13个网页的任务大约须要12秒钟。函数

e879583925acaaf687ad9d97b52bab54.png

Python学习交流群:1004391443性能

2,多线程学习

如今咱们改进一下这个程序,咱们能够将读取url的任务分配给多个线程来完成,而不是只让一个线程去逐一读取。网站

好比4个线程:url

5963e34d6f0a10f8854cc6ec80f45c80.png

8个线程:操作系统

a2f70d6ad1e0f66e65336a29a78dacfa.png

16个线程:

860ee85712d9f9faec157bbf601fcb56.png

用到16个线程时,这个任务的耗时已经从12.3秒缩短到了1.32秒。

使用多线程能够显著加快许多与io绑定的任务。在这里,读取url所花费的大部分时间是因为网络延迟。与io绑定的程序大部分时间都在等待输入/输出,无所事事。这多是来自网络、数据库、文件甚至用户的I/O。这种I/O每每要花费大量的时间,由于源自己可能须要在传递I/O以前执行本身的处理。例如,CPU的工做速度比网络链接传输数据的速度快得多。

多线程能够显著提升咱们爬取网页任务的效率。

3,多重处理

另外一个能够提升效率的手段是多重处理。

好比咱们有一个任务是计算100万之内全部质数的和。

若是只用单个进程:

9b2ff588169b234c430fb932682833ec.png

若是使用多进程:

fe2fed5850b6d4443d1ae353b0f98b9f.png

和多线程相似,多进程也是将任务(好比判断一系列数是不是质数)拆分再汇总,以此提升效率。

因为现代CPU一般有多个核心,咱们能够经过使用多处理模块来加快CPU绑定任务的速度。CPU绑定任务是花费大部分时间在CPU上执行计算的程序(数学计算、图像处理等)。若是计算能够彼此独立地执行,咱们就能够将它们分配到可用的CPU内核中,从而显著提升处理速度。

咱们所要作的就是:

1,定义要应用的函数

2,准备要应用功能的项目列表

3,使用Pool生成进程。传递给Pool()的数字将是生成的进程数。在with语句中嵌入能够确保在完成执行后终止进程。

4,使用池进程的map函数组合输出。映射函数的输入是要应用于每一个项的函数,以及项列表。

注意:能够定义该函数,以便执行任何能够并行执行的任务。例如,函数可能包含将计算结果写入文件的代码。

那么,为何咱们须要单独的多处理和多线程呢?若是您尝试使用多线程来提升CPU绑定任务的性能,而当进程数超过某个数值时,您可能会注意到,实际上获得的是性能降低。让咱们看看为何会这样。

由于Python也带有全局解释器锁(GIL)。Python会很乐意让用户生成任意数量的线程,可是GIL确保在任何给定的时间只有一个线程执行。

对于一个io绑定的任务,这彻底没问题。一个线程向一个URL发出请求,当它等待响应时,能够将该线程替换为向另外一个URL发出另外一个请求的另外一个线程。由于一个线程在收到响应以前不须要作任何事情,因此在给定的时间内只执行一个线程并不重要。

对于CPU绑定的任务,由于一次只执行一个线程,即便生成多个线程,而且每一个线程都有本身的数目来检查素数,CPU仍然一次只处理一个线程。实际上,这些数字仍然会被一个接一个地检查。若是在CPU绑定的任务中使用多线程,那么处理多线程的开销将致使性能降低。

为了克服这个“限制”,咱们使用了多处理模块。多处理不是使用线程,而是使用多个进程。每一个进程都有本身的解释器和内存空间,所以GIL不会阻止任何事情。本质上,每一个进程使用不一样的CPU内核同时处理不一样的数字。

您可能会注意到,与使用简单的for循环,甚至多线程相比,使用多处理时CPU利用率要高得多。这是由于您的程序使用多个CPU内核,而不只仅是一个内核。

请记住,多处理自己就有管理多个进程的开销,这一般比多线程开销更大。(多处理生成一个单独的解释器,并为每一个进程分配一个单独的内存空间)这意味着,根据经验,当可使用轻量级多线程时,最好使用它(io绑定任务)。当CPU处理成为瓶颈时,一般须要调用多处理模块。但请记住,能力越大,责任越大。

若是一次生成的进程超过CPU的处理能力,您将注意到性能开始降低。这是由于操做系统如今必须作更多的工做来交换CPU内核内外的进程,由于您的进程比内核多。实际状况可能比简单的解释要复杂得多,但这是基本思想。当咱们达到16个进程时,您能够看到个人系统性能降低。这是由于个人CPU只有16个逻辑核心。

743accae3b3597685342c7328190bd86.png

4,总结

对于io绑定的任务,使用多线程能够提升性能。

对于io绑定的任务,使用多处理也能够提升性能,可是开销每每比使用多线程高。

Python GIL意味着在Python程序的任何给定时间内只能执行线程。

对于CPU绑定的任务,使用多线程实际上会下降性能。

对于CPU绑定的任务,使用多处理能够提升性能。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值