平行程式設計是一種程式設計模型,允許程式在多個處理器或核心上同時執行多個任務。該模型旨在更有效地使用處理器資源、減少處理時間並提高效能。
為了用圖像說明並行編程,我們可以想像我們遇到了一個問題。在開始並行處理之前,我們將這個問題分成更小的子部分。我們假設這些子部分彼此獨立且彼此不了解。每個子問題都轉換為更小的任務或指令。這些任務以適合併行工作的方式組織。例如,可以建立許多指令來對資料集執行相同的操作。然後這些任務被分配給不同的處理器。每個處理器獨立且並行地處理其分配的指令。這個過程顯著減少了總處理時間,使我們能夠更有效地使用資源。
Python 提供了多種用於平行程式設計的工具和模組。
**多處理
**它允許程式同時運行多個進程,從而利用真正的並行性。多處理模組克服了 GIL(全域解釋器鎖)的限制,允許在多核心處理器上實現全部效能。
全域解釋器鎖定(GIL)是流行的 Python 實作(稱為 CPython)中使用的一種機制。 GIL 一次只允許一個執行緒執行 Python 字節碼。當在 Python 中使用多執行緒時,這種結構會限制真正的並行性。
*平方和立方計算範例
*
from multiprocessing import Process def print_square(numbers): for n in numbers: print(f"Square of {n} is {n * n}") def print_cube(numbers): for n in numbers: print(f"Cube of {n} is {n * n * n}") if __name__ == "__main__": numbers = [2, 3, 4, 5] # İşlemler (processes) oluşturma process1 = Process(target=print_square, args=(numbers,)) process2 = Process(target=print_cube, args=(numbers,)) # İşlemleri başlatma process1.start() process2.start() # İşlemlerin tamamlanmasını bekleme process1.join() process2.join()
為什麼我們需要多重處理 我們可以用廚師和廚房的類比來解釋多重處理的需求。您可以將廚師獨自在廚房做飯視為單一進程程序。我們可以將其比作多處理,即多個廚師在同一個廚房一起工作。
單一流程 - 單一烹飪
廚房裡只有一名廚師。這位廚師將製作三道不同的菜餚:開胃菜、主菜和甜點。每道菜依序製作:
他準備並完成了開胃菜。
他繼續主菜並完成它。
最後,他做了甜點。
問題:
無論廚師有多快,他或她都會輪流,這會浪費廚房時間。
如果需要同時煮三種不同的菜餚,時間會更長。
多重處理 - 許多廚師
現在想像一下同一個廚房裡有三個廚師。每個人都在準備不同的菜餚:
開胃菜由一名廚師製作。
第二位廚師準備主菜。
第三位廚師做甜點。
優點:
三道菜同時製作,大大減少了總時間。
每個廚師獨立做自己的工作,不受其他人的影響。
在 Python 中的進程之間共享資料
在Python中,可以使用多處理模組在不同進程之間共用資料。但是,每個進程都使用自己的記憶體空間。因此,使用特殊的機制在進程之間共享資料。
from multiprocessing import Process def print_square(numbers): for n in numbers: print(f"Square of {n} is {n * n}") def print_cube(numbers): for n in numbers: print(f"Cube of {n} is {n * n * n}") if __name__ == "__main__": numbers = [2, 3, 4, 5] # İşlemler (processes) oluşturma process1 = Process(target=print_square, args=(numbers,)) process2 = Process(target=print_cube, args=(numbers,)) # İşlemleri başlatma process1.start() process2.start() # İşlemlerin tamamlanmasını bekleme process1.join() process2.join()
當我們檢查程式碼範例時,我們看到結果清單為空。主要原因是使用多處理創建的進程在自己的記憶體空間中工作,獨立於主進程。由於這種獨立性,子進程中所做的更改不會直接反映在主進程中的變數中。
Python 提供了以下共享資料的方法:
**1。共享記憶體
**Value 和 Array 物件用於在操作之間共用資料。
值:共享單一資料類型(例如數字)。
數組:用於共享資料數組。
import multiprocessing result = [] def square_of_list(mylist): for num in mylist: result.append(num**2) return result mylist= [1,3,4,5] p1 = multiprocessing.Process(target=square_of_list,args=(mylist,)) p1.start() p1.join() print(result) # [] Boş Liste
**2。隊列
**它使用 FIFO(先進先出)結構在進程之間傳輸資料。
multiprocessing.Queue 允許多個進程發送和接收資料。
from multiprocessing import Process, Value def increment(shared_value): for _ in range(1000): shared_value.value += 1 if __name__ == "__main__": shared_value = Value('i', 0) processes = [Process(target=increment, args=(shared_value,)) for _ in range(5)] for p in processes: p.start() for p in processes: p.join() print(f"Sonuç: {shared_value.value}")
**3。管道
**multiprocessing.Pipe 提供兩個進程之間的雙向資料傳輸。
它可用於發送和接收資料。
from multiprocessing import Process, Queue def producer(queue): for i in range(5): queue.put(i) # Kuyruğa veri ekle print(f"Üretildi: {i}") def consumer(queue): while not queue.empty(): item = queue.get() print(f"Tüketildi: {item}") if __name__ == "__main__": queue = Queue() producer_process = Process(target=producer, args=(queue,)) consumer_process = Process(target=consumer, args=(queue,)) producer_process.start() producer_process.join() consumer_process.start() consumer_process.join()
*進程之間的填充
*「進程之間的填充」通常用於進程記憶體組織或避免存取多個進程之間共享的資料時的資料對齊和衝突問題。
這個概念在快取行錯誤共享等情況下尤其重要。當多個進程嘗試同時使用共享記憶體時,錯誤共享可能會導致效能損失。這是由於現代處理器中快取行的共享。
**進程之間的同步
**使用Python中的多處理模組,多個進程可以同時運作。然而,當多個進程需要存取相同的資料時,使用同步非常重要。這是確保數據一致性並避免競爭條件等問題所必需的。
from multiprocessing import Process, Pipe def send_data(conn): conn.send([1, 2, 3, 4]) conn.close() if __name__ == "__main__": parent_conn, child_conn = Pipe() process = Process(target=send_data, args=(child_conn,)) process.start() print(f"Alınan veri: {parent_conn.recv()}") # Veri al process.join()
鎖定一次只允許一個程序存取共享資料。
在使用鎖的進程完成之前,其他進程會等待。
**多執行緒
多執行緒是一種平行程式設計模型,允許程式同時運行多個執行緒。執行緒是在同一進程中運行的較小的獨立程式碼單元,旨在透過共享資源實現更快、更有效率的處理。
在Python中,threading模組用於開發多執行緒應用程式。然而,由於Python的全域解釋器鎖定(GIL)機制,多執行緒在CPU密集型任務上提供的效能有限。因此,多執行緒通常是 I/O 密集型任務的首選。
執行緒是我們程式中的指令序列。
from multiprocessing import Process def print_square(numbers): for n in numbers: print(f"Square of {n} is {n * n}") def print_cube(numbers): for n in numbers: print(f"Cube of {n} is {n * n * n}") if __name__ == "__main__": numbers = [2, 3, 4, 5] # İşlemler (processes) oluşturma process1 = Process(target=print_square, args=(numbers,)) process2 = Process(target=print_cube, args=(numbers,)) # İşlemleri başlatma process1.start() process2.start() # İşlemlerin tamamlanmasını bekleme process1.join() process2.join()
**線程同步
**執行緒同步是當多個執行緒同時存取相同資源時用於保證資料一致性和順序的技術。在Python中,threading模組提供了幾種用於同步的工具。
**為什麼需要執行緒同步?
**比賽條件:
當兩個或多個執行緒同時存取共享資源時,可能會出現資料不一致的情況。
例如,一個執行緒可能讀取數據,而另一個執行緒更新相同的數據。
*資料一致性:
*
需要執行緒之間的協調來確保共享資源正確更新。
Python 中的同步工具範例
**1.鎖
**當一個執行緒取得鎖時,它會等待鎖被釋放,然後其他執行緒才能存取相同資源。
import multiprocessing result = [] def square_of_list(mylist): for num in mylist: result.append(num**2) return result mylist= [1,3,4,5] p1 = multiprocessing.Process(target=square_of_list,args=(mylist,)) p1.start() p1.join() print(result) # [] Boş Liste
2 活動
from multiprocessing import Process, Value def increment(shared_value): for _ in range(1000): shared_value.value += 1 if __name__ == "__main__": shared_value = Value('i', 0) processes = [Process(target=increment, args=(shared_value,)) for _ in range(5)] for p in processes: p.start() for p in processes: p.join() print(f"Sonuç: {shared_value.value}")
**結論:
**執行緒同步對於防止執行緒存取共享資源時出現資料不一致至關重要。 Python中,Lock、RLock、Semaphore、Event、Condition等工具根據同步需求提供了有效的解決方案。使用哪種工具取決於應用程式的需求和同步要求。
以上是Python 中的進程管理:平行程式設計基礎的詳細內容。更多資訊請關注PHP中文網其他相關文章!