首页 > 代码库 > multiprocessing总结
multiprocessing总结
由于GIL的存在,python的多线程并不是真正的多线程。如果想充分的时候多核CPU的资源,在Cpython中大部分情况下需要使用到多进程(multiprocess)。
Python通过“multiprocessing”来实现多进程并发的功能。
multiprocessing支持的功能:
- 子进程
- 进程间通信/共享
- 进程同步
在使用multiprocessing时候的注意点:
- 在UNIX平台上,当某个进程终结之后,该对其父进程调用wait,否则进程将成为僵尸进程(Zombie),所以每个Process对象都需要调用join()方法。
- multiprocessing提供了IPC(inter process communication),推荐使用Queue或pipe
- 多进程应该避免资源共享,因为会增加复杂性和降低程序效率
- 在windows下,子进程的启动必须在 if __name__ == "__main__":语句后面
创建多进程的方法:
1,直接传入
2,从Process类继承
直接传入代码:
1 from multiprocessing import Process 2 3 def foo(num): 4 print("sub_process :", num) 5 6 if __name__ =="__main__": 7 for i in range(10): 8 p = Process(target=foo,args=(i,)) 9 p.start() 10 p.join()
通过类实现代码:
1 from multiprocessing import Process 2 3 class Myprocess(Process): 4 def __init__(self,arg): 5 super(Myprocess,self).__init__() 6 self.arg = arg 7 8 def run(self): 9 print("sub_process :" , self.arg) 10 11 if __name__ == "__main__": 12 for i in range(10): 13 p = Myprocess(i) 14 p.start() 15
-----------------------------------------------------------------------------------------------------------------------------------------------------
Process类
构造方法:
Process([group , [target ,[name ,[ args ,[kwargs ] ] ] ] ] )
group:线程组
target:要执行的函数
name:进程名字
args/kwargs:函数的参数
实例方法:
is_alive():返回进程是否正在运行
join([timeout[):阻塞当前上下文环境的进程,直到调用此方法的进程终止或到达指定的timeout(可选参数)。
start():进程准备就绪,等待CPU调用
run():start()调用run方法
terminate():不管任务是否完成,立即停止工作进程
属性:
name:进程名
pid:进程号
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
pool类:(进程池)
进程池内部维护一个进程序列,当使用时,则去进程池中获取一个进程,如果进程池序列中没有可供使用的进程,那么程序就会等待,之道进程池中有可用进程为止。
进程池数量最好等于CPU核心数量。
构造方法:
Pool([processes , [ initializer , [ initargs , [ maxtasksperchild , [ context ] ] ] ] ])
- processes:使用的工作进程数量,如果processes是None,那么使用os.cpu_count()返回的数量
- initializer:如果initializer是None,那么每一个工作进程在开始的时候会调用initializer(*initargs)
- maxtasksperichild:工作进程退出之前可以完成的任务数,完成后用一个新的工作进程来替换原进程,来让限制的资源被释放。默认值为None,意味着只要pool存在,工作进程就会一直存活。
- context:用在指定工作进程启动时的上下文,一般使用multiprocessing.Pool()或者一个context对象的pool()方法来创建一个池,两种方法都适当的设置了context
实例方法:
apply (fun , [ args , [ kwargs ] ] ):同步进程池
apply_async(fun , [args, [ kwargs [ callback , [error_callback ] ] ] ] )异步进程池
close()关闭进程池,阻止更多的任务提交到pool,待任务完成后,工作进程会退出。
terminate():结束工作进程,不在处理未完成的任务
join():wait工作线程的退出,在调用join()前,必须调用close() or terminate()。这是因为被终止的进程需要被父进程调用wait(join与wait等价),否则进程会成为僵尸进程。
例子:(异步进程池)
1 def foo(num): 2 time.sleep(2) 3 print(‘Run process : %d‘ % num) 4 5 def bar(arg): 6 print("Error") 7 8 if __name__ == "__main__": 9 pool = Pool(8) 10 for i in range(16): 11 pool.apply_async(func=foo , args=(i,) , error_callback=bar) 12 pool.close() 13 pool.join() 14 print("---Run Over---")
例子:(同步进程池)
1 #!/usr/bin/env python3 2 #-*- coding:utf-8 -*- 3 4 from multiprocessing import Pool 5 import time 6 7 def foo(num): 8 time.sleep(2) 9 print(‘Run process : %d‘ % num) 10 11 def bar(arg): 12 print("Error") 13 14 if __name__ == "__main__": 15 pool = Pool(8) 16 for i in range(16): 17 pool.apply(func=foo,args=(i,)) 18 pool.close() 19 pool.join() 20 print("---Run Over---")
区别:
异步进程池在调用进程的时候没有顺序,同步有顺序,但是同步牺牲了效率。
multiprocessing总结