線程與進程的區別:python
進程:資源的集合mysql
線程:最小調度單位redis
信號量:也至關因而locksql
守護線程:服務於非守護線程;緩存
quene:程序的解耦;提升效率;也是有序的容器;隊列只有一份數據,取完了就沒有了網絡
先進先出(FIFO)多線程
後進先出(LIFO)app
生產者消費者模型:也就是爲了實現解耦框架
event:事件---紅綠燈實驗ssh
i/o不佔用cpu,計算佔用
python多線程不適合cpu密集型操做任務,適合i/o密集型任務
推薦的書:
《失控》,《必然》
《數學之美》,《浪潮之巔》
雞湯總結:作一個有素質的人
今天的課程:
1、多進程
解決多核問題而生
單個進程:
#!/usr/bin/env python # -*- coding:utf-8 -*- import multiprocessing,time def run(name): #定義函數 time.sleep(1) print('hello',name) if __name__ == '__main__': p = multiprocessing.Process(target=run,args=('hehe',)) #實例化一個進程 p.start() #執行進程 p.join() #進程等待
多進程:
#!/usr/bin/env python # -*- coding:utf-8 -*- import multiprocessing,time def run(name): print('hello',name) time.sleep(1) if __name__ == '__main__': for i in range(10): #定義循環 p = multiprocessing.Process(target=run,args=("hehe %s"%i,)) p.start()
獲取進程id:
#!/usr/bin/env python # -*- coding:utf-8 -*- import multiprocessing,os def info(title): #信息展現函數 print(title) print('module name:',__name__) #打印模塊名稱 print('parent process id',os.getppid()) #父進程id獲取 print('process id',os.getpid()) #當前進程id print('\n\n') def f(name): #定義功能函數 info('\033[31;1mfunction f\033[0m') print('hello',name) if __name__ == '__main__': #主進程調用 info('\033[32;1mmain process line\033[0m') p = multiprocessing.Process(target=f,args=('hehe',)) #定義進程 p.start() #開始進程 p.join() #進程等待
每個子進程都是有其父進程啓動的
進程間通訊:Queue
#!/usr/bin/env python # -*- coding:utf-8 -*- from multiprocessing import Queue,Process def f(qq): qq.put([122,None,'heheheda']) #父進程放入數據 if __name__ == '__main__': q = Queue() p = Process(target=f,args=(q,)) #將q傳給子進程p p.start() print(q.get()) p.join()
此時的q也就是pickle序列化和 反序列化以後的結果了,實現了進程間的通訊
管道pipe:
#!/usr/bin/env python # -*- coding:utf-8 -*- from multiprocessing import Process,Pipe def f(conn): conn.send([123,'sada',None]) #子進程send數據 conn.send([12223,'s343ada321',None]) #子進程send數據 print(conn.recv()) #子進程接受父進程數據 conn.close() if __name__ == '__main__': parent_conn,chile_conn = Pipe() #生成一個管道實例 p = Process(target=f,args=(chile_conn,)) #實例化 p.start() print(parent_conn.recv()) #父進程接收數據 print(parent_conn.recv()) #父進程接收數據 # print(parent_conn.recv()) #父進程接收數據,若是子進程不發送數據,父進程就處於等待狀態 parent_conn.send('hello child!!') #父進程給子進程發送數據 p.join()
mananger:實現進程間數據共享
#!/usr/bin/env python # -*- coding:utf-8 -*- #Author:wanghui from multiprocessing import Manager,Process import os def f(d,l): d[os.getpid()] = os.getpid() #獲取pid l.append(os.getpid()) print(l) if __name__ == '__main__': with Manager() as manager: d = manager.dict() #生成一個字典,可在多個進程間共享和傳遞 l = manager.list(range(5)) #生成一個列表,可在多個進程間共享和傳遞數據 p_list = [] for i in range(5): p = Process(target=f,args=(d,l)) p.start() p_list.append(p) for res in p_list: #等待結果 res.join() print(d) print(l)
結果以下:
D:\pythom35\python.exe D:/project/s14/day10/manager2.py [0, 1, 2, 3, 4, 7828] [0, 1, 2, 3, 4, 7828, 4180] [0, 1, 2, 3, 4, 7828, 4180, 1800] [0, 1, 2, 3, 4, 7828, 4180, 1800, 8076] [0, 1, 2, 3, 4, 7828, 4180, 1800, 8076, 7264] {1800: 1800, 4180: 4180, 8076: 8076, 7828: 7828, 7264: 7264} #進程字典打印結果 [0, 1, 2, 3, 4, 7828, 4180, 1800, 8076, 7264]
進程鎖:實現進程同步
#!/usr/bin/env python # -*- coding:utf-8 -*- from multiprocessing import Process,Lock def f(l,i): ''' :param l: 鎖 :param i: 傳進來的內容 :return: ''' # l.acquire() print('hehehe',i) #l.release() if __name__ == '__main__': lock = Lock() for num in range(100): #修改進程的啓動數量 Process(target=f,args=(lock,num)).start() #啓動進程
進程池:
#!/usr/bin/env python # -*- coding:utf-8 -*- from multiprocessing import Process,Pool import time,os def Foo(i): time.sleep(1) print('in process',os.getpid()) return i + 100 def Bar(arg): print("-->exec done",arg,os.getpid()) #獲取子進程pid if __name__ == '__main__': pool = Pool(5) #容許進程池裏同時放入5個進程 print('主進程',os.getpid()) #獲取主進程pid for i in range(10): #啓動10個進程 pool.apply_async(func=Foo,args=(i,),callback=Bar) #異步執行(並行),須要執行join ,callback:回調 #pool.apply(func=Foo,args=(i,)) #將Foo放入進程池,串行 print('end') pool.close() pool.join() #進程池中進程執行完畢後再關閉,若是註釋,那麼程序直接關閉。.join()
2、協程
又名微線程,輕量級線程;
協程擁有本身的寄存器上下文和棧;協程