#先来看下如何实现多进程
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 | # multiprocessing 这个是python的多进程的模块,我们会用到这个模块的很多方法 from multiprocessing import Process import threading import time def f(name): time.sleep( 2 ) print ( "hello," ,name) if __name__ = = '__main__' : p1 = Process(target = f,args = ( "bob" ,)) p2 = Process(target = f, args = ( "aob" ,)) #多进程 # p1 = threading.Thread(target=f,args=("bob",)) # p2 = threading.Thread(target=f,args=("add",)) # 多线程 p1.start() p2.start() p1.join() |
进程和进程之间是不能共享数据的,比如我们看下面的例子
1 2 3 4 5 6 7 8 9 | import multiprocessing from multiprocessing import Queue def test_func(): test_queue.put( "aa" ) if __name__ = = '__main__' : test_queue = Queue() test_func() print (test_queue.get()) |
结果如下
1 |
我们在看一个例子,通过子进程去运行函数test_func()
1 2 3 4 5 6 7 8 9 10 11 | import multiprocessing from multiprocessing import Queue def test_func(): test_queue.put( "aa" ) if __name__ = = '__main__' : test_queue = Queue() p = multiprocessing.Process(target = test_func) p.start() # test_func() # print(test_queue.get()) |
下面我们来讲解下
第一个例子,我们从头到尾只有一个进程在执行,所以在函数test_func中,可以直接使用外面定义的变量队列
第二个例子,我们通过子进程去启动函数test_func,由于子进程和自己的父进程不是同一个进程,所以,在test_func中不能直接使用变量队列,运行脚本会直接报错的,此时我们如想在子线程中使用变量队列,就只能通过函数传参的方式将队列传递进去,就比如下面的例子
1 2 3 4 5 6 7 8 9 10 11 | import multiprocessing from multiprocessing import Queue def test_func(test_queue): test_queue.put( "aa" ) if __name__ = = '__main__' : test_queue = Queue() p = multiprocessing.Process(target = test_func,args = (test_queue,)) p.start() print (test_queue.get()) |
#在看来子进程和父进程
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 | from multiprocessing import Process import os def info(title): print (title) print ( "module name," ,__name__) print ( "parent process," ,os.getppid()) print ( "process id," ,os.getpid()) print ( "\n\n" ) def f(name): info( "function f" ) print ( "hello," ,name) if __name__ = = '__main__' : info( "main process line" ) #在主线程中调用info这个函数,所有这里执行的infor的函数的父进程是pycharm,而子进程id就是执行这个脚本的进程本身的id p = Process(target = info,args = ( "bob" ,)) #这里是在多线程中调用info这个函数,调用info这个函数,那么在这里执行info这个函数,打印的父进程就是脚本本身这个进程id,而 #这里的info函数的id就是一个新的进程id p.start() p.join() ''' 程序的执行结果如下 main process line module name, __main__ parent process, 3132 process id, 9180 bob module name, __mp_main__ parent process, 9180 process id, 5204 ''' |
#然后来看下通过Queue来实现进程之间数据交互
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 | #不同进程之间的内存数据是不共享的,可以用下面的方法实现进程间的内存共享,要通过一个第三方才能通信,这里我们介绍第一个方法:用队列Queue来实现 #Queue有2个方法,一个put,一个是get,队列一定是先进先出 from multiprocessing import Process from multiprocessing import Queue def f(q): q.put({ "k1" : "v1" }) q.put([ "1" , "2" , "3" ]) q.put([ "2" , "2" , "2" ]) print (q.qsize()) #获取队列queue的大小 if __name__ = = '__main__' : que = Queue() que.qsize() p = Process(target = f,args = (que,)) #这里执行这个函数,就是在执行这个脚本的进程id的子进程id p.start() print ( "from parent," ,que.get()) print ( "from parent," , que.get()) #这里的进程id就是执行这个脚本的进程id<br> #这里要注意,que.get如果拿不到数据,则会一直阻塞<br> p.join() # 结果如下 ''' 2 from parent, {'k1': 'v1'} from parent, ['1', '2', '3 ''' |
#通过pipe来实现进程之间交互
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 | #前面我们学习了进程之间交互数据的方法Queue,今天我们在来学习一下管道来实现进程之间的内存交互 # pipe管道,也是进程间通讯的一种方式,会返回一对对象,2个对象分别是管道的两头,一个管道是有2头,一头赋值给子进程,一头赋值给你父进程 from multiprocessing import Process #导入多进程这个方法 from multiprocessing import Pipe #导入管道这个方法 def f(conn): conn.send([ "a" , "b" , "c" ]) conn.send([ "1" , "2" , "3" ]) conn.close() #在子进程里send一个数据,然后关闭管道 if __name__ = = '__main__' : parent_conn,child_conn = Pipe() #生成一个管道,一端是父进程,一端是子进程 p = Process(target = f,args = (child_conn,)) #用子进程启动函数f,f这个函数就往管道里send数据 p.start() #启动上面定义的子进程 print (parent_conn.recv()) #通过父进程去管道中获取数据,并打印 print (parent_conn.recv()) # parent_conn.recv() # 这个recv这个方法也是阻塞的,如果没有recv到数据,则该管道会一直阻塞 p.join() #等待这子进程执行完毕在退出 |
判断pipe的缓冲区是否还有数据poll(timeout=xxx)方法
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 | import multiprocessing def test(conn): conn.send( "123" ) conn.send( "456" ) conn.close() print (conn.writable) if __name__ = = '__main__' : p_conn,c_conn = multiprocessing.Pipe() p = multiprocessing.Process(target = test,args = [c_conn,]) p.start() # print(dir(p_conn)) print (p_conn.recv()) print (p_conn.recv()) if not p_conn.poll(timeout = 2 ): print ( "kong....." ) p.join() |
分类:
python
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· Linux系列:如何用heaptrack跟踪.NET程序的非托管内存泄露
· 开发者必知的日志记录最佳实践
· SQL Server 2025 AI相关能力初探
· Linux系列:如何用 C#调用 C方法造成内存泄露
· AI与.NET技术实操系列(二):开始使用ML.NET
· 被坑几百块钱后,我竟然真的恢复了删除的微信聊天记录!
· 没有Manus邀请码?试试免邀请码的MGX或者开源的OpenManus吧
· 【自荐】一款简洁、开源的在线白板工具 Drawnix
· 园子的第一款AI主题卫衣上架——"HELLO! HOW CAN I ASSIST YOU TODAY
· 无需6万激活码!GitHub神秘组织3小时极速复刻Manus,手把手教你使用OpenManus搭建本