进程通信,队列,管道

【一】进程通信

1.多个进程之间的信息交换过程
2.如何实现
  (1)消息队列:把信息从一端放入队列中,另一个进程从另一端将消息取出
      非阻塞的,即发送进程不需要等待接收进程的响应即可继续执行。
  (2)管道:半双工的通信机制,同时只能一端进行发一端进行收,不能同时收发
  (3)队列(管道+锁):生产者-消费者模型。先进先出
  

【二】队列

(1)创建队列的类(底层就是以管道和锁定的方式实现)
    语法:import queue
        q = queue.Queue(maxsize)
       maxsize是队列中允许最大项数,省略则无大小限制。 
    from multiprocessing import Queue
        q = Queue(5)
(2)方法:
记住:队是先进先出的数据结构
   1.队列对象.put(数据)入队<--->相当于push,将数据放入到队列中
    如果blocked为True(默认值),并且timeout为正值,该方法会阻塞timeout指定的时间,直到该队列有剩余的空间。如果超时,会抛出Queue.Full异常
    如果blocked为False,但该Queue已满,会立即抛出Queue.Full异常。
    
   2.队列对象.get()出队<--->相当于pop,将数据读出并删除
    如果blocked为True(默认值),并且timeout为正值,那么在等待时间内没有取到任何元素,会抛出Queue.Empty异常。
    如果blocked为False,有两种情况存在,如果Queue有一个值可用,则立即返回该值,否则,如果队列为空,则立即抛出Queue.Empty异常.
    
   3.队列对象.get_nowait()=====  同q.get(False),但是当没有值时会报错
   4.队列对象.put_nowait()=====  同q.get(False),但是当队列满时会报错
   5.队列对象.empty()===判空
   6.队列对象.full()===判满
   7.队列对象.qsize()====判队列中数据的数量
"""
    full()
    empty()
    get_nowait()
上述方法能否在并发的场景下精准使用???
    不能用!!!
    
之所以介绍队列是因为它可以支持进程间数据通信
"""
​

【三】管道

管道:半双工的通信机制,同时只能一端进行发一端进行收,不能同时收发
#Pipe
from multiprocessing import Pipe
# 创建管道对象,获取两个管道对象,可以用一个变量装到时候解包
left_pipe,right_pipe=Pipe()#默认参数dumplex:默认双通道管道
# 方法(都是要先关闭一端一端接或收)传递或接收完记得关闭刚刚在使用的管道
# (1)接收数据
"""
left_pipe.close()
right_pipe.recv()
# (2)发送数据
left_pipe.close()
right_pipe.send()

【四】进程间通信(IPC机制)

1.方式一:子进程与主进程之间通过队列进行通信
  直接把队列当作一个子进程进行存放消息
  from multiprocessing import Process, Queue
# 创建一个子进程函数
def producer(que_ue):
    # 子进程放入消息
    que_ue.put('子进程中放入了一条消息')
    print('这是主进程中的一个子进程的队列')
if __name__ == '__main__':
    # 【一】创建队列对象:注意这里是使用的 multiprocessing 里面的 Queue
    que_ue = Queue()
    # 【二】创建子进程:目标函数和参数带进去
    pro_cess = Process(target=producer, args=(que_ue,))
    # 【三】启动子进程
    pro_cess.start()
    # 【四】主进程获取消息
    msg_from_p = que_ue.get()
​
    # 【五】查看消息
    print(msg_from_p)
    # 这是主进程中的一个子进程的队列
    # 子进程中放入了一条消息
    
2.方式二:子进程与子进程之间借助队列进行通信
    生产者消费者的思想,生产者往队列放消息,消费者从队列拿数据
    from multiprocessing import Process, Queue
# 创建一个子进程函数
def producer(que_ue):
    # 子进程放入消息
    que_ue.put('子进程中放入了一条消息')
    print('这是主进程中的一个子进程的队列')
def customer(que_ue):
    # 在另一个子进程中获取到非本子进程放入的消息
    msg_from_producer = que_ue.get()
    print('这是来自另一个子进程的消息 :>>>> ', msg_from_producer)
if __name__ == '__main__':
    # 【一】创建队列对象:注意这里是使用的 multiprocessing 里面的 Queue
    que_ue = Queue()
    # 【二】创建子进程:目标函数和参数带进去
    p_list = []
    pro_producer = Process(target=producer, args=(que_ue,))
    pro_customer = Process(target=customer, args=(que_ue,))
    # 【三】启动子进程
    pro_producer.start()
    pro_customer.start()
​
    pro_producer.join()
    pro_customer.join()
​
    # 这是主进程中的一个子进程的队列
    # 这是来自另一个子进程的消息 :>>>>  子进程中放入了一条消息

【四】生产者消费者模型

# 生产者
    负责生产/制作数据
# 消费者
    负责消费/处理数据
"""

【五】JoinableQueue模块

● JoinableQueue([maxsize]):这就像是一个Queue对象,但队列允许项目的使用者通知生成者项目已经被成功处理。
● 通知进程是使用共享的信号和条件变量来实现的。
from multiprocessing import JoinableQueue
    
q = JoinableQueue()
​
# 方法介绍:JoinableQueue的实例p除了与Queue对象相同的方法之外还具有:
​
# q.task_done():使用者使用此方法发出信号,表示q.get()的返回项目已经被处理。如果调用此方法的次数大于从队列中删除项目的数量,将引发ValueError异常
​
# q.join():生产者调用此方法进行阻塞,直到队列中所有的项目均被处理。阻塞将持续到队列中的每个项目均调用q.task_done()方法为止

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值