[Python][微進階]Queue佇列中的資料被多個執行緒並行處理

閱讀時間約 8 分鐘

在Python中,queue是一個非常有用的模块。

它提供了多種佇列(queue)實現,用於在多線程環境中安全地交換信息或者數據

佇列(queue)是一種先進先出(FIFO)的數據結構,允許在佇列的一端插入元素,另一端取出元素。(FIFO First In, First Out 的縮寫)

FIFO

FIFO


以下是Python中queue模塊的基本用法及相關說明:

創建佇列

使用Queue類來創建一個佇列對象。可以指定佇列的最大長度,如果不指定,則默認為無限長度的佇列。

import queue

q = queue.Queue(maxsize=10) # 創建一個最大長度為10的佇列



放入元素

使用put()方法向佇列中放入一個元素。

q.put(item)



取出元素

使用get()方法從佇列中取出一個元素,如果佇列為空,則會阻塞直到有元素可用。

item = q.get()


判斷佇列是否為空

使用empty()方法可以判斷佇列是否為空。

if q.empty():
print("Queue is empty")


判斷佇列是否已滿

使用full()方法可以判斷佇列是否已滿,僅適用於有限長度的佇列。


設置阻塞與非阻塞操作

默認情況下,佇列的put()get()操作是阻塞的,如果你想要非阻塞的行為,可以使用put_nowait()get_nowait()方法。

q.put_nowait(item)
item = q.get_nowait()


佇列的阻塞操作

佇列的阻塞操作意味着當佇列為空時,get()操作將會等待直到有元素可用;當佇列已滿時,put()操作將會等待直到有空間可用。這樣可以很容易地實現生產者-消費者模式。

程式範例說明解釋阻塞與非阻塞操作



非阻塞操作

import queue

my_queue = queue.Queue(maxsize=2)

# 使用 put_nowait() 方法放入元素,即使佇列已滿也不會等待
try:
my_queue.put_nowait("Item 1")
my_queue.put_nowait("Item 2")
my_queue.put_nowait("Item 3") # 這裡會引發異常,因為佇列已滿
except queue.Full:
print("Queue is full, unable to put item.")

# 使用 get_nowait() 方法取出元素,即使佇列為空也不會等待
try:
item1 = my_queue.get_nowait()
item2 = my_queue.get_nowait()
item3 = my_queue.get_nowait() # 這裡會引發異常,因為佇列為空
except queue.Empty:
print("Queue is empty, unable to get item.")



輸出

Queue is full, unable to put item.
Queue is empty, unable to get item.


阻塞操作

import queue
import time
my_queue = queue.Queue(maxsize=2)

# 使用 put_nowait() 方法放入元素,即使佇列已滿也不會等待
# 時間計數來確認,等待多久才,等待多久才引發異常
start_time = time.time()
try:
my_queue.put("Item 1", timeout=1) #若未設定timout將會無限期等待
my_queue.put("Item 2", timeout=1)
my_queue.put("Item 3", timeout=1) # 這裡會引發異常,因為佇列已滿,等待一秒若無資料則會引發異常
except queue.Full:
print("Queue is full, unable to put item.")

end_time = time.time()
print(f'put處理時間 :{(end_time - start_time):6f}秒')
# 使用 get_nowait() 方法取出元素,即使佇列為空也不會等待

start_time = time.time()
try:
item1 = my_queue.get(timeout=1)
item2 = my_queue.get(timeout=1)
item3 = my_queue.get(timeout=1) # 這裡會引發異常,因為佇列為空
except queue.Empty:
print("Queue is empty, unable to get item.")

end_time = time.time()
print(f'put處理時間 :{(end_time - start_time):6f}秒')



輸出

Queue is full, unable to put item.
put處理時間 :1.001525
Queue is empty, unable to get item.
put處理時間 :1.000238

程式範例

主要流程如下:

1.創建一個佇列 my_queue,並將10個資料放入佇列中

放入佇列示意圖

放入佇列示意圖

2.創建兩個Plan執行緒 Plan_APlan_B,並將佇列物件和執行緒編號傳遞給它們。

3.啟動兩個執行緒,使其同時開始取出佇列中的資料。

取出Queue資料

取出Queue資料

4.使用join()方法等待兩個執行緒完成處理。

5.印出 "Done." 表示處理完成

import time
import threading
import queue

# Plan 類別
class Plan(threading.Thread):
def __init__(self, queue, num):
threading.Thread.__init__(self)
self.queue = queue
self.num = num

def run(self):
while self.queue.qsize() > 0:
# 取得新的資料
msg = self.queue.get()
# 印出資料
print(f'Plan_{self.num} : {msg}')
time.sleep(1)

# 建立佇列
my_queue = queue.Queue()

for i in range(10):
my_queue.put(f'Data : {i}')
print(f'查看佇列資料長度: {my_queue.qsize()}')

# 建立兩個 Plan
Plan_A = Plan(my_queue, 'A')
Plan_B = Plan(my_queue, 'B')

# 讓 Worker 開始取出資料
Plan_A.start()
Plan_B.start()

# 等待所有 Worker 結束
Plan_A.join()
Plan_B.join()

print("Done.")

輸出

查看佇列資料長度: 10
Plan_A : Data : 0
Plan_B : Data : 1
Plan_A : Data : 2
Plan_B : Data : 3
Plan_A : Data : 4
Plan_B : Data : 5
Plan_A : Data : 6
Plan_B : Data : 7
Plan_A : Data : 8
Plan_B : Data : 9
Done.

參考文獻

[Python][微進階]threading 多執行緒平行處理

https://docs.python.org/zh-tw/3/library/queue.html#module-queue

119會員
201內容數
本業是影像辨識軟體開發,閒暇時間進修AI相關內容,將學習到的內容寫成文章分享。
留言0
查看全部
發表第一個留言支持創作者!
螃蟹_crab的沙龍 的其他內容
當你需要在 Python 中執行多個任務,但又不希望它們相互阻塞時,可以使用 threading 模組。 threading 模組允許你在單個程序中創建多個執行緒,這些執行緒可以同時運行,從而實現並行執行多個任務的效果。
在這篇文章中,我們講述瞭如何使用numpy.where方法查找Numpy數組中值的索引。除了介紹了numpy.where的基本用法外,還舉了一些應用實例進行了詳細說明。文章最後提供了其他應用領域以及相關參考文獻。
f字符串(f-string)在Python 3.6版本引入了新特性,可以更方便地格式化字符串。本文介紹了f-string的基本使用方法,以及表達式、運算符、格式化控制、字典和列表的應用,以及調用方法和函數等。f-string提供了一種更靈活的方式,使你能夠控制字符串的外觀,以滿足不同情況下的需求。
NumPy 提供了一種 N 維數組類型 ndarray(N-dimensional array) ,它描述了相同類型的「數據類型」的集合。 多維數組: ndarray 是一個 N 維數組,其中 N 可以是任意整數。一維數組是向量,二維數組是矩陣
NumPy在圖像處理、機器學習、數學和統計學等領域中被廣泛應用。 以下是一些常見的應用場景: 數據處理和分析: NumPy提供了高效的多維數組(nd array)和相應的操作函數,使得對大型數據集進行快速、有效的操作變得容易。
在程式開發中,協作合作專案時,利用type hint,可以快速知道函式輸入及輸出的資料型別,在後續的維護時也會更加方便及可讀。 Type hints 是Python 3.5 版本引入的功能,它允許在函數宣告中指定參數和傳回值的類型。Type hints 是一種可選的註解形式,不會影響程式碼的運行,
當你需要在 Python 中執行多個任務,但又不希望它們相互阻塞時,可以使用 threading 模組。 threading 模組允許你在單個程序中創建多個執行緒,這些執行緒可以同時運行,從而實現並行執行多個任務的效果。
在這篇文章中,我們講述瞭如何使用numpy.where方法查找Numpy數組中值的索引。除了介紹了numpy.where的基本用法外,還舉了一些應用實例進行了詳細說明。文章最後提供了其他應用領域以及相關參考文獻。
f字符串(f-string)在Python 3.6版本引入了新特性,可以更方便地格式化字符串。本文介紹了f-string的基本使用方法,以及表達式、運算符、格式化控制、字典和列表的應用,以及調用方法和函數等。f-string提供了一種更靈活的方式,使你能夠控制字符串的外觀,以滿足不同情況下的需求。
NumPy 提供了一種 N 維數組類型 ndarray(N-dimensional array) ,它描述了相同類型的「數據類型」的集合。 多維數組: ndarray 是一個 N 維數組,其中 N 可以是任意整數。一維數組是向量,二維數組是矩陣
NumPy在圖像處理、機器學習、數學和統計學等領域中被廣泛應用。 以下是一些常見的應用場景: 數據處理和分析: NumPy提供了高效的多維數組(nd array)和相應的操作函數,使得對大型數據集進行快速、有效的操作變得容易。
在程式開發中,協作合作專案時,利用type hint,可以快速知道函式輸入及輸出的資料型別,在後續的維護時也會更加方便及可讀。 Type hints 是Python 3.5 版本引入的功能,它允許在函數宣告中指定參數和傳回值的類型。Type hints 是一種可選的註解形式,不會影響程式碼的運行,
你可能也想看
Google News 追蹤
Thumbnail
這個秋,Chill 嗨嗨!穿搭美美去賞楓,裝備款款去露營⋯⋯你的秋天怎麼過?秋日 To Do List 等你分享! 秋季全站徵文,我們準備了五個創作主題,參賽還有機會獲得「火烤兩用鍋」,一起來看看如何參加吧~
Thumbnail
美國總統大選只剩下三天, 我們觀察一整週民調與金融市場的變化(包含賭局), 到本週五下午3:00前為止, 誰是美國總統幾乎大概可以猜到60-70%的機率, 本篇文章就是以大選結局為主軸來討論近期甚至到未來四年美股可能的改變
想要開始Python語言的開發環境,有兩種常見方式,一種是下載安裝到本機端,另一種是直接在雲端執行。本文將介紹三個常見的開發工具及其安裝步驟。
隨著數據越來越成為商業和決策的關鍵因素,數據科學變得越來越重要。而Python,作為一個強大且多用途的編程語言,在數據科學領域中佔有重要地位。不管你是想在工作上提升技能,還是在個人生活中探索數據,Python都可以幫助你解鎖數據的力量。本文將介紹Python在數據科學中的應用,並提供一些入門指南,讓
Thumbnail
網路爬蟲(web crawler),也叫網路蜘蛛(spider) 是一個強大的自動化工具,可以自由瀏覽、擷取訪問網頁的各項資訊,例如:新聞文章、電商商品價格,當專案中需要添加外部數據或進行大量資料收集時,網路爬蟲就是一個非常實用的工具。
Thumbnail
探索Python學習筆記中列表的建立、存取和常用方法。從使用中括號定義列表到了解索引、新增、刪除、修改等操作,並介紹append、remove、count等常用方法。
Thumbnail
在本篇Python學習筆記中,我們探討了字典的建立與存取,以及常用方法,字典是一種強大的資料型態,透過key和value的對應關係存儲和取得資料,我們學會了建立字典、存取資料、新增/修改/刪除項目,以及取得key和value的方法,字典是Python中不可或缺的工具!
Thumbnail
我們可以利用工作表的append()方法,在工作表的列尾添加資料列。 利用迴圈的技巧,我們可以批次賦予區塊內所有儲存格相同的值。 我們也可以在指定的列(行)之前插入指定數量的空白列(行),從指定的列(行)開始向下(右)刪除指定數量的列(行)。
Thumbnail
我希望透過在好學校開設「Python 的 50+ 練習:資料科學學習手冊」,讓學生一步步完成這門課程所有的觀念講解、範例實作以及練習之後,扎實地將 Python 程式設計與資料科學應用納入自己的技能組,成為一位擅長寫程式處理資料的分析師,大幅提升工作掌握度與職涯發展性!
Thumbnail
Python 從創立之初的沒沒無名,至今被譽為「初學者最佳語言」,在 Python  社群背後默默貢獻的「鄉民」們居功厥偉!讓我們來看一下 Python 那些年的歷歷往事。
Thumbnail
這個秋,Chill 嗨嗨!穿搭美美去賞楓,裝備款款去露營⋯⋯你的秋天怎麼過?秋日 To Do List 等你分享! 秋季全站徵文,我們準備了五個創作主題,參賽還有機會獲得「火烤兩用鍋」,一起來看看如何參加吧~
Thumbnail
美國總統大選只剩下三天, 我們觀察一整週民調與金融市場的變化(包含賭局), 到本週五下午3:00前為止, 誰是美國總統幾乎大概可以猜到60-70%的機率, 本篇文章就是以大選結局為主軸來討論近期甚至到未來四年美股可能的改變
想要開始Python語言的開發環境,有兩種常見方式,一種是下載安裝到本機端,另一種是直接在雲端執行。本文將介紹三個常見的開發工具及其安裝步驟。
隨著數據越來越成為商業和決策的關鍵因素,數據科學變得越來越重要。而Python,作為一個強大且多用途的編程語言,在數據科學領域中佔有重要地位。不管你是想在工作上提升技能,還是在個人生活中探索數據,Python都可以幫助你解鎖數據的力量。本文將介紹Python在數據科學中的應用,並提供一些入門指南,讓
Thumbnail
網路爬蟲(web crawler),也叫網路蜘蛛(spider) 是一個強大的自動化工具,可以自由瀏覽、擷取訪問網頁的各項資訊,例如:新聞文章、電商商品價格,當專案中需要添加外部數據或進行大量資料收集時,網路爬蟲就是一個非常實用的工具。
Thumbnail
探索Python學習筆記中列表的建立、存取和常用方法。從使用中括號定義列表到了解索引、新增、刪除、修改等操作,並介紹append、remove、count等常用方法。
Thumbnail
在本篇Python學習筆記中,我們探討了字典的建立與存取,以及常用方法,字典是一種強大的資料型態,透過key和value的對應關係存儲和取得資料,我們學會了建立字典、存取資料、新增/修改/刪除項目,以及取得key和value的方法,字典是Python中不可或缺的工具!
Thumbnail
我們可以利用工作表的append()方法,在工作表的列尾添加資料列。 利用迴圈的技巧,我們可以批次賦予區塊內所有儲存格相同的值。 我們也可以在指定的列(行)之前插入指定數量的空白列(行),從指定的列(行)開始向下(右)刪除指定數量的列(行)。
Thumbnail
我希望透過在好學校開設「Python 的 50+ 練習:資料科學學習手冊」,讓學生一步步完成這門課程所有的觀念講解、範例實作以及練習之後,扎實地將 Python 程式設計與資料科學應用納入自己的技能組,成為一位擅長寫程式處理資料的分析師,大幅提升工作掌握度與職涯發展性!
Thumbnail
Python 從創立之初的沒沒無名,至今被譽為「初學者最佳語言」,在 Python  社群背後默默貢獻的「鄉民」們居功厥偉!讓我們來看一下 Python 那些年的歷歷往事。