由于Python中线程封锁机制,导致Python中的多线程并不是正真意义上的多线程。当我们有并行处理需求的时候,可以采用多进程迂回地解决。
如果要在主进程中启动大量的子进程,可以用进程池的方式批量创建子进程。
首先,创建一个进程池子,然后使用apply_async()
方法将子进程加入到进程池中。
import multiprocessing
import os
import time
from datetime import datetime
def subprocess(number):
# 子进程
print('这是第%d个子进程' % number)
pid = os.getpid() # 得到当前进程号
print('当前进程号:%s,开始时间:%s' % (pid, datetime.now().isoformat()))
time.sleep(30) # 当前进程休眠30秒
print('当前进程号:%s,结束时间:%s' % (pid, datetime.now().isoformat()))
def mainprocess():
# 主进程
print('这是主进程,进程编号:%d' % os.getpid())
t_start = datetime.now()
pool = multiprocessing.Pool()
for i in range(8):
pool.apply_async(subprocess, args=(i,))
pool.close()
pool.join()
t_end = datetime.now()
print('主进程用时:%d毫秒' % (t_end - t_start).microseconds)
if __name__ == '__main__':
# 主测试函数
mainprocess()
对Pool
对象调用join()
方法会等待所有子进程执行完毕,调用join()
之前必须先调用close()
,调用close()
之后就不能继续添加新的Process了。
可能的运行结果:
这是主进程,进程编号:10264
这是第0个子进程
当前进程号:10688,开始时间:2017-04-05T11:23:47.039989
这是第1个子进程
当前进程号:10152,开始时间:2017-04-05T11:23:47.055615
这是第2个子进程
当前进程号:5764,开始时间:2017-04-05T11:23:47.055615
这是第3个子进程
当前进程号:6392,开始时间:2017-04-05T11:23:47.055615
这是第4个子进程
当前进程号:9744,开始时间:2017-04-05T11:23:47.055615
这是第5个子进程
当前进程号:2636,开始时间:2017-04-05T11:23:47.071240
这是第6个子进程
当前进程号:6788,开始时间:2017-04-05T11:23:47.071240
这是第7个子进程
当前进程号:1604,开始时间:2017-04-05T11:23:47.071240
当前进程号:10688,结束时间:2017-04-05T11:24:17.053047
当前进程号:10152,结束时间:2017-04-05T11:24:17.062183
当前进程号:5764,结束时间:2017-04-05T11:24:17.062183
当前进程号:9744,结束时间:2017-04-05T11:24:17.062183
当前进程号:6392,结束时间:2017-04-05T11:24:17.062183
当前进程号:2636,结束时间:2017-04-05T11:24:17.072177
当前进程号:6788,结束时间:2017-04-05T11:24:17.072177
当前进程号:1604,结束时间:2017-04-05T11:24:17.072177
主进程用时:255168毫秒
官方API文档说明:
close()
Prevents any more tasks from being submitted to the pool. Once all the tasks have been completed the worker processes will exit.
join()
Wait for the worker processes to exit. One must call close() or terminate() before using join().