----------基础篇
进程池引入
为什么要用进程池呢?如果我们有几百上千个任务需要自行,那么按照之前的做法,我们就要创建几百上千个进程,每一个进程都要占用一定的内存空间,进程间的切换也费时,系统开销很大,而且,难道这成千上百个进程能同时并发执行的有几个呢?其实也就那么几个子,所以,根本没必要创建那么多进程。那么怎么办呢?那就创建进程池。进程池里有固定数量的进程,每次执行任务时都从进程池中取出一个空闲进程来执行,如果任务数量超过进程池中进程数量,那么就等待已经在执行的任务结束之后,有进程空闲之后再执行,也就是说,同一时间,只有固定数量的进程在执行,这样对操作系统得压力也不会太大,效率也得到保证。
在利用Python进行系统管理的时候,特别是同时操作多个文件目录,或者远程控制多台主机,并行操作可以节约大量的时间。多进程是实现并发的手段之一,需要注意的问题是:
- 很明显需要并发执行的任务通常要远大于核数
- 一个操作系统不可能无限开启进程,通常有几个核就开几个进程
- 进程开启过多,效率反而会下降(开启进程是需要占用系统资源的,而且开启多余核数目的进程也无法做到并行)
Pool可以提供指定数量的进程,供用户调用,当有新的请求提交到pool中时,如果池还没有满,那么就会创建一个新的进程用来执行该请求;但如果池中的进程数已经达到规定最大值,那么该请求就会等待,直到池中有进程结束,才会创建新的进程来它。
1.POOL
Pool([numprocess [,initializer [, initargs]]])
:创建进程池
参数介绍:
- numprocess:要创建的进程数,如果省略,将默认使用
cpu_count()
的值 - initializer:是每个工作进程启动时要执行的可调用对象,默认为None
- initargs:是要传给initializer的参数组
方法介绍:
p.apply(func [, args [, kwargs]])
在一个池工作进程中执行func(*args,**kwargs),然后返回结果。
需要强调的是:此操作并不会在所有池工作进程中并执行func函数。如果要通过不同参数并发地执行func函数,必须从不同线程调用p.apply()
函数或者使用p.apply_async()
p.apply_async(func [, args [, kwargs]])
在一个池工作进程中执行func(*args,**kwargs),然后返回结果。
此方法的结果是AsyncResult类的实例,callback是可调用对象,接收输入参数。当func的结果变为可用时,
将理解传递给callback。callback禁止执行任何阻塞操作,否则将接收其他异步操作中的结果。p.close()
:关闭进程池,防止进一步操作。如果所有操作持续挂起,它们将在工作进程终止前完成p.jion()
:等待所有工作进程退出。此方法只能在close()
或teminate()
之后调用
代码学习
import random,time,os
from multiprocessing import Pool
def func(n):
print('任务{}开始执行,进程为:{}'.format(n,os.getpid()))
time.sleep(random.randint(1,4))
print('任务{}结束执行,进程为:{}'.format(n,os.getpid()))
if __name__ == '__main__':
p=Pool(3) #c创建一个进程池,里面有三个进程
for i in range(5):
res=p.apply(func,args