参考博客:https://blog.csdn.net/u013066730/article/details/105821979
信安赛以前没试过这样的开发,这次信安赛的作品涉及并发编程,就记录记录呢。 大体逻辑是:主进程运行Flask框架,子进程跑检测数字人的模型,子进程的参数应该传递到主进程中才能实时显示到前端 还学了怎么在浏览器的控制台debug前端JS脚本hhh
1.关于进程里的全局变量 import multiprocessingimport timelist1=[] def write (): for i in range (5 ): list1.append(i) time.sleep(1 ) def read (): print (list1) if __name__=="__main__" : t1=multiprocessing.Process(target=write) t2=multiprocessing.Process(target=read) t1.start() t1.join t2.start()
执行上述进程可以看到t1
列表中有值,而t2
列表还是一个空值列表,所以由此可见在不同的进程中 它们是不共享全局变量的,只有在线程中 才共享全局变量。
2.多进程通信 一个demo:
from multiprocessing import Process, Managerimport timeimport randomdef kkk (a_list, number ): for i in range (10 ): a_list.append(np.array([i])) time.sleep(random.randrange(2 )) print ('这是进程{} {}' .format (number, a_list)) print ('这是进程{} {}' .format (number, a_list)) def jjj (a_list ): for i in range (2 ): process = Process(target=kkk, args=(a_list, i)) process.start() if __name__ == '__main__' : manager = Manager() a_list = manager.list () process_0 = Process(target=jjj, args=(a_list,)) process_0.start() process_0.join() print (a_list) print (len (a_list)) print ('it\'s ok' )
由于进程之间数据是不共享的,所以不会出现多线程GIL带来的问题。多进程之间的通信通过Queue()或Pipe()来实现
2.1.1.Queue() 使用方法跟threading里的queue差不多
from multiprocessing import Process, Queue def f (q ): q.put([42 , None , 'hello' ]) if __name__ == '__main__' : q = Queue() p = Process(target=f, args=(q,)) p.start() print (q.get()) p.join()
2.1.2.Pipe() Pipe的本质是进程之间的数据传递,而不是数据共享,这和socket有点像。pipe()返回两个连接对象分别表示管道的两端,每端都有send()和recv()方法。如果两个进程试图在同一时间的同一端进行读取和写入那么,这可能会损坏管道中的数据。
from multiprocessing import Process, Pipe def f (conn ): conn.send([42 , None , 'hello' ]) conn.close() if __name__ == '__main__' : parent_conn, child_conn = Pipe() p = Process(target=f, args=(child_conn,)) p.start() print (parent_conn.recv()) p.join()
2.2 Manager 通过Manager可实现进程间数据的共享。Manager()返回的manager对象会通过一个服务进程,来使其他进程通过代理的方式操作python对象。manager对象支持 list
, dict
, Namespace
, Lock
, RLock
, Semaphore
, BoundedSemaphore
, Condition
, Event
, Barrier
, Queue
, Value
,Array
.
from multiprocessing import Process, Manager def f (d, l ): d[1 ] = '1' d['2' ] = 2 d[0.25 ] = None l.append(1 ) print (l) if __name__ == '__main__' : with Manager() as manager: d = manager.dict () l = manager.list (range (5 )) p_list = [] for i in range (10 ): p = Process(target=f, args=(d, l)) p.start() p_list.append(p) for res in p_list: res.join() print (d) print (l)