一 : 概述
进程间通信(IPC)的方式有N种,这里我们学习FIFO队列和管道
二 : 队列的创建和使用
队列可以由multiprocessing.Queue创建,它是多线程安全的,可以实现多进程之间的数据传递.
创建 : Queue([maxsize]) , maxsize是队列中允许的最大元素数.默认为0,意为无限制.
将Queue类实例化得到对象q,q具有如下方法:
q.get( [ block [ , timeout ] ] ), 这个方法用于返回q中的第一个元素,如果为空,则阻塞,直到有元素可用为止,参数block用于控制阻塞行为,默认为True,若设置为False,则不会阻塞,引发Queue.Empty异常,参数timeout为超时时间,用在阻塞模式中,若在指定的时间内没有元素可用,引发Queue.Empty异常.
q.get_nowait()相当于block设定为False的get()方法.
q.put( item, [ , block [ , timeout ] ] ) ,将item放入队列,如果队列已满,则阻塞,直到有空间可用为止,,参数block用于控制阻塞行为,默认为True,若设置为False,则不会阻塞,引发Queue.Full异常,参数timeout为超时时间,用在阻塞模式中,若在指定的时间内没有元素可用,引发Queue.Full异常.
q.put_nowait(item),相当于block设定为False的put()方法.
q.qsize(),返回队列中目前项目的数量,不过该函数的结果并不可靠.
q.empty(),调用此方法时,如果队列为空,则返回True,不过结果不可靠,因为在返回结果和使用队列中间,可能有其他进程对队列进行了修改.
q.full(),与empt()方法相反,如果队列已经满了,则返回True,也是不可靠的,原因相同.
q.close(),关闭队列,无法再put()和get()
''' multiprocessing模块支持进程间通信的两种主要形式:管道和队列 都是基于消息传递实现的,但是队列接口 ''' from multiprocessing import Queue q=Queue(3) #put ,get ,put_nowait,get_nowait,full,empty q.put(3) q.put(3) q.put(3) # q.put(3) # 如果队列已经满了,程序就会停在这里,等待数据被别人取走,再将数据放入队列。 # 如果队列中的数据一直不被取走,程序就会永远停在这里。 try: q.put_nowait(3) # 可以使用put_nowait,如果队列满了不会阻塞,但是会因为队列满了而报错。 except: # 因此我们可以用一个try语句来处理这个错误。这样程序不会一直阻塞下去,但是会丢掉这个消息。 print('队列已经满了') # 因此,我们再放入数据之前,可以先看一下队列的状态,如果已经满了,就不继续put了。 print(q.full()) #满了 print(q.get()) print(q.get()) print(q.get()) # print(q.get()) # 同put方法一样,如果队列已经空了,那么继续取就会出现阻塞。 try: q.get_nowait(3) # 可以使用get_nowait,如果队列满了不会阻塞,但是会因为没取到值而报错。 except: # 因此我们可以用一个try语句来处理这个错误。这样程序不会一直阻塞下去。 print('队列已经空了') print(q.empty()) #空了
加入进程通信中
import time from multiprocessing import Process, Queue def f(q): q.put([time.asctime(), 'from Eva', 'hello']) #调用主函数中p进程传递过来的进程参数 put函数为向队列中添加一条数据。 if __name__ == '__main__': q = Queue() #创建一个Queue对象 p = Process(target=f, args=(q,)) #创建一个进程 p.start() print(q.get()) p.join()
三 : 使用队列实现生产者消费者模型
1. 什么是生产者消费者模型
生产者消费者模式是通过一个容器来解决生产者和消费者的强耦合问题。生产者和消费者彼此之间不直接通讯,而通过阻塞队列来进行通讯,所以生产者生产完数据之后不用等待消费者处理,直接扔给阻塞队列,消费者不找生产者要数据,而是直接从阻塞队列里取,阻塞队列就相当于一个缓冲区,平衡了生产者和消费者的处理能力。
2. 为什么使用这个模型
在线程世界里,生产者就是生产数据的线程,消费者就是消费数据的线程。在多线程开发当中,如果生产者处理速度很快,而消费者处理速度很慢,那么生产者就必须等待消费者处理完,才能继续生产数据。同样的道理,如果消费者的处理能力大于生产者,那么消费者就必须等待生产者。为了解决这个问题于是引入了生产者和消费者模式。
3. 基于队列实现该模型
from multiprocessing import Process,Queue import time,random,os def consumer(q): while True: res=q.get() time.sleep(random.randint(1,3)) print('