在需要频繁的创建删除较多进程的情况下,导致计算机资源消耗过多
进程池如何处理
1. 创建进程池,在池内放入适量的进程
2. 将事件加入进程池等待队列
3. 使用进程池中的进程不断处理事件
4. 所有事件处理后,回收关闭进程池
from multiprocessing import Pool
Pool()
功能 : 创建进程池
参数 : processes : 指定进程池中进程数量
返回 : 得到进程池对象
pool.apply_async()
功能 : 异步方式将事件放入进程池执行
参数 : func : 要执行的事件函数
args : 同Process中args 给函数传参
kwds : 同Process中kwargs 给函数传参
返回值 : 返回一个对象 该对象可以通过get()方法得到 func函数的返回值
pool.close()
功能 : 关闭进程池,使其无法加入新的事件
pool.join()
功能 : 阻塞等待进程池退出 (当所有事件处理完毕后)
pool.apply()
用法和apply_async一样,只是需要顺序执行,一个事件结束在执行另一个事件
pool.map(func,iter)
功能 : 类似于内建函数map 将第二个参数的迭代数传递个第一个参数的函数执行。同时兼容了使用进程池执行
返回值: 返回func的返回值列表
r = pool.map(fun,test)===>
r = []
for i in test:
res = pool.apply_async(fun,(i,))
r.append(res.get())
进程间通信
磁盘交互 : 1. 速度慢
2. 不安全
socket 本地套接字
管道 消息队列 共享内存 信号 信号量 套接字
管道通信 pipe
在内存中开辟一块空间,对多个进程可见,通过管道,多进程进行通信
multiprocessing --- 》 Pipe
fd1,fd2 = Pipe(duplex = True)
功能 : 创建一个管道
参数 : duplex 默认为True 表示双向管道
设置为False 则表示单向管道
返回值 : 返回两个管道流对象,表示管道的两端
如果是双向管道则连个均可读写
如果为单向管道则,fd1只能读,fd2只能写
fd1.recv()
功能 : 接收消息 (每次接收一条)
参数 : 无
返回值: 接收到的消息
* 如果管道没有消息会阻塞
fd2.send(data)
功能 : 发送消息 可以是字符串或其他类型
参数:要发送的内容
* 如果没有接收端则管道破裂
消息队列
队列 : 先进先出
在内存中开辟队列模型,用来存放消息。认可拥有队列的进程都可以存取消息
创建队列
q = Queue(maxsize = 0)
功能 : 创建一个消息队列
参数 : maxsize 默认为0 表示队列可存放消息由内存而定
> 0 表示队列最多存放多少条消息
返回值 : 返回消息队列对象
q.put()
功能 : 向队列中存放消息
参数 : 要存的消息 (字符串 整数 列表)
* 当队列满时会阻塞
q.full()
判断队列是否为满 满返回True
q.get()
功能 : 向队列中取出消息
返回值 :取出的消息
* 当队列空时会阻塞
q.empty()
判断队列是否为空 空返回True
q.qsize()
得到当前队列中消息的个数
q.close() 关闭队列
* put get中均有可选参数 block 和timeout
block 默认为True 表示阻塞函数 如果设置为False则不阻塞
timeout block 为True 时 设置超时时间
共享内存
在内存中开辟一段空间,存储数据,对多个进程可见。每次写入共享内存的数据会覆盖之前的内容。由于对内存格式化较少,所以存取速度快
from multiprocessing import Value,Array
obj = Value(ctype,obj)
功能 : 开辟共享内存空间
参数 : ctype str 要转变的c类型 (对照ctype表)
obj 写入共享内存的初始值
返回值 : 返回一个共享内存对象
obj.value 即可得到共享内存中的值
obj = Array(ctype,obj)
功能 : 开辟共享内存空间
参数 : ctype 要转换的类型
obj 存入到共享内存中的数据
是一个列表,要求列表中数类型一致
正整数,则表示开辟一个多大的序列空间
返回值: 返回一个共享内存对象
管道 消息队列 共享内存
开辟空间 内存 内存 内存
读写方式 双向/单向 先进先出 操作覆盖内存
效率 一般 一般 快
应用 多用于亲 方便灵活 较复杂
缘进程 广泛
是否需要 否 否 需要
互斥机制
信号
一个进程向另一个进程通过信号传递某种讯息
kill -l 查看信号
kill -signame PID 给PID的进程发送一个信号
关于信号:
信号名称 : 系统定义,信号的名字
信号的含义 : 系统定义 ,信号的作用
信号的默认处理方法 : 系统定义,信号给接收进程带来的行为 一般有 终止 暂停 忽略
python 如何操作信号
发送
os.kill(pid,sig)
功能:向一个进程发送一个信号
参数 : pid : 要发送信号的进程PID
sig : 要发送的信号
signal.alarm(sec)
功能 : 向自身发送一个时钟信号 SIGALRM
参数 : sec 时钟秒数
* 信号属于异步通信方式,信号的发送不会影响进程的持续执行
*一个进程中只能同时有一个时钟,后面的时钟时间会覆盖前面的
处理 :
signal.pause()
功能: 阻塞等待一个信号的发生