1、multiprocessing模塊簡介——進程基於「threading」的接口編程
multiprocessing模塊支持建立進程——使用threading模塊類似的API。multiprocessing模塊對本地和遠程的併發都提供了支持,使用子進程(subprocesses)來替代threads解決了GIL的限制。所以,multiprocessing模塊容許程序充分利用給定設備的多核資源。在Unix和Windows系統均可以運行。安全
multiprocessing模塊一樣引入了threading模塊不支持的APIs。主要例子如:Pool對象提供了便捷並行執行(有多輸入)的函數的執行,經過進程分發輸入數據。下面就是一個簡單的數據分發。多線程
from multiprocessing import Pool def f(x): return x*x if __name__ == '__main__': p = Pool(5) print(p.map(f, [1, 2, 3]))
2、Process類併發
在multiprocessing模塊中,processes能夠經過建立一個Process對象產生。而後調用其start()方法。Process和threading.Thread遵循threading.Thread的API。一個簡單的多線程例子以下ide
from multiprocessing import Process def f(name): print 'hello', name if __name__ == '__main__': p = Process(target=f, args=('bob',)) p.start() p.join()
顯示相應的單個進程IDs,以下:函數
from multiprocessing import Process import os import time def info(title): print(title) print('module name:', __name__) if hasattr(os, 'getppid'): print('parent process:',os.getppid()) print('process id:', os.getpid()) def f(name): time.sleep(2) info('function f') print('hello', name) if __name__ == '__main__': info('main line') p = Process(target=f,args=('bob',)) p.start() p.join()
3、Exchanging objects between processes進程間通信ui
一、Queue基本上是Queue.Queue的克隆版,可是本Queue是線程和進程都安全的spa
from multiprocessing import Process, Queue import time def f(q): time.sleep(2) q.put([42, None, 'hello']) print('f') if __name__ == '__main__': q = Queue() p = Process(target=f, args=(q,)) p.start() p.join() print('hello') print(q.get())
二、Pipes是Pipe()函數返回一個鏈接對象對——由一個pipe鏈接,默認是雙工(兩種方式)線程
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()
Pipe()返回兩個鏈接(Connection)對象,表明管道的兩端。每一個鏈接對象都有send()和recv()方法(彼此之間)。code
注意:若是兩個線程(或進程)同時嘗試從pipe的同一端讀寫數據,管道里的數據可能損壞。若是同時在pipe()的兩端讀寫是沒有風險的。
4、進程間的同步機制
multiprocessing擁有threading模塊相同的同步機制。例如,能夠使用lock來保證一次只有一個進程打印到標準輸出。
from multiprocessing import Process,Lock import time def f(l, i): l.acquire() # time.sleep(2) print('hello world', i) l.release() if __name__ == '__main__': lock = Lock() for num in range(10): Process(target=f,args=(lock, num)).start()
5、進程間共享狀態
如上所述,咱們在作併發編程時,應當儘量避免使用共享狀態。有其是多進程。然而,你非得在多進程使用共享數據,multiprocessing提供了幾種方來實現。
一、Shared memory共享內存
數據能夠存儲在共享內存裏使用Value或Array。例如,以下代碼: