zoukankan      html  css  js  c++  java
  • python-- 进程管道 Pipe、进程 Manager

    进程管道 Pipe

    管道之间通信是不安全的

    from multiprocessing import Pipe
    
    con1,con2 = Pipe()

    管道是用于多进程之间通信的一种方式。如果在单进程中使用管道,那么就是con1收数据,就是con2发数据。如果是con1发数据,就是con2收数据如果在多进程中使用管道,那么就必须是父进程使用con1收,子进程就必须使用con2发

    父进程使用con1发,子进程就必须使用con2收

    父进程使用con2收,子进程就必须使用con1发

    父进程使用con2发,子进程就必须使用con1收

    在管道中有一个著名的错误叫做EOFError。是指,父进程中如果关闭了发送端,子进程还继续接收数据,那么就会引发EOFError。

    from multiprocessing import Pipe, Process
    
    
    def func(con):
        con1, con2 = con
        con1.close()  # 子进程使用con2和父进程通信,所以
        while 1:
            try:
                print(con2.recv())  # 当主进程的con1发数据时,子进程要死循环的去接收。
            except EOFError:  # 如果主进程的con1发完数据并关闭con1,子进程的con2继续接收时,就会报错,使用try的方式,获取错误
                con2.close()  # 获取到错误,就是指子进程已经把管道中所有数据都接收完了,所以用这种方式去关闭管道
                break
    
    
    if __name__ == '__main__':
        con1, con2 = Pipe()
        p = Process(target=func, args=((con1, con2),))
        p.start()
        con2.close()  # 在父进程中,使用con1去和子进程通信,所以不需要con2,就提前关闭
        for i in range(10):  # 生产数据
            con1.send(i)  # 给子进程的con2发送数据
        con1.close()  # 生产完数据,关闭父进程这一端的管道

    结果:

    0
    1
    2
    3
    4
    5
    6
    7
    8
    9

    from multiprocessing import Process, Pipe
    
    
    def f(conn):
        conn.send([42, None, 'hello fromchild'])
        conn.send([42, None, 'hello fromchild2'])
        print("from parent:", conn.recv())
        conn.close()
    
    
    if __name__ == '__main__':
        parent_conn, child_conn = Pipe()  # 需要两个参数接收
        p = Process(target=f, args=(child_conn,))
        p.start()
        print(parent_conn.recv())
        print(parent_conn.recv())
        parent_conn.send("范冰冰")

    结果:

    [42, None, 'hello fromchild']
    [42, None, 'hello fromchild2']
    from parent: 范冰冰

    parent_conn, child_conn = Pipe()生成管道实例,相当于socket通信,一头在主进程,一头在子进程,就可以实现进程之间的数据的传递

    进程 Manager

    Queue,Pipe只能实现进程之间数据的传递,Manager可以进行数据之间的共享
    from multiprocessing import Manager, Value
    
    m = Manager()
    num = m.dict({键: 值})
    num = m.list([1, 2, 3])

    from multiprocessing import Process, Manager
    
    
    def func(num):
        num[0] -= 1  # num[0] = 1
        print('子进程中的num的值是', num)
    
    
    if __name__ == '__main__':
        m = Manager()
        num = m.list([1, 2, 3])
        p = Process(target=func, args=(num,))
        p.start()
        p.join()
        print('父进程中的num的值是', num)

    结果:

    子进程中的num的值是 [0, 2, 3]
    父进程中的num的值是 [0, 2, 3]

  • 相关阅读:
    非法字符:"ufeff"
    IntelliJ IDEA 创建Web项目
    dubbo 响应超时异常: com.alibaba.dubbo.remoting.TimeoutException: Waiting server-side response timeout.
    Spring Cacheable 注解不缓存null值
    linux 中 permission denied的问题
    unZip/Zip的安装
    @GeneratedValue 四种标准用法为TABLE,SEQUENCE,IDENTITY,AUTO
    【nginx】nginx tomcat session 共享配置
    [IDEA] IDEA 集成PlantUML
    【linux】 解决linux下vsftp 500 OOPS: cannot change directory:/home/ftp/ 办法
  • 原文地址:https://www.cnblogs.com/zouzou-busy/p/13775382.html
Copyright © 2011-2022 走看看