python中的 生產者和消費者

什麼是生產者消費者模式

在軟件開發過程中,經常會遇到這樣的情景:
某些模塊負責生產數據,這些數據由其他模塊來負責處理(此處的模塊可能是:函數、線程、進程等)。產生數據的模塊稱爲生產者,而處理數據的模塊稱爲消費者。在生產者與消費者之間的緩衝區稱之爲倉庫。生產者負責往倉庫運輸商品,而消費者負責從倉庫裏取出商品,這就構成了生產者消費者模式。

結構圖:
在這裏插入圖片描述
舉個栗子:
假如珍妮要寄一封信,大致過程如下
1、珍妮把信寫好 —— 相當於生產者生產數據 
2、珍妮把信放入郵箱 —— 相當於生產者把數據放入緩衝區
3、郵遞員把信從郵箱取出,做相應處理 —— 相當於消費者把數據取出緩衝區,處理數據

生產者消費者模式優點

1、解耦
假設生產者和消費者分別是兩個線程。如果讓生產者直接調用消費者的某個方法,那麼生產者對於消費者就會產生依賴(也就是耦合)。如果未來消費者的代碼發生變化,可能會影響到生產者的代碼。而如果兩者都依賴於某個緩衝區,兩者之間不直接依賴,耦合也就相應降低了。

2、併發
由於生產者與消費者是兩個獨立的併發體,他們之間是用緩衝區通信的,生產者只需要往緩衝區裏丟數據,就可以繼續生產下一個數據,而消費者只需要從緩衝區拿數據即可,這樣就不會因爲彼此的處理速度而發生阻塞。

3、忙閒不均
當生產者製造數據快的時候,消費者來不及處理,未處理的數據可以暫時存在緩衝區中,慢慢處理掉。而不至於因爲消費者的性能造成數據丟失或影響生產者生產。

下面用代碼實現一下:

代碼演示:

from queue import Queue
import threading
import time

#創建隊列
q = Queue(10)

def producer(name):
    """生產者"""
    count = 1 # 給生產者的信計數
    while True:
        q.join() #等待task_done()發送信號
        q.put(count)
        print("%s正在寫第%d封信"%(name,count))
        count += 1
        time.sleep(0.1)

def customer(name):
    """消費者"""
    count = 1
    while True:
        x = q.get()
        print("%s正在取第%d封信"%(name,x))
        count += 1
        q.task_done() #取完後發送信號
        time.sleep(1)
        
if __name__ == '__main__':
    t1 = threading.Thread(target=producer,args=("珍妮",))
    t2 = threading.Thread(target=customer,args=("郵遞員",))
    t1.start()
    t2.start()

運行結果:
在這裏插入圖片描述

今天就寫這裏
在這裏插入圖片描述

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章