[英]python: if key not in dictionary add the key. preventing race conditions with multiple threads
我正在編程一個電報機器人,其中更多線程可以處理每個更新異步操作。 我用硬編碼編寫一個空字典,並且在運行bot時,有多個線程對其進行讀寫。
最常見的操作是:
if key not in dict:
dict[key] = value
else:
dict[key].append(another_value)
問題在於,當線程檢查dict中是否包含key時,也許不是,另一個線程在其中寫入了key。
所以基本上我必須擺脫這種賽車狀況。
我需要一個快速的解決方案。 在網上搜索時,我發現了關於threading.Lock()
答案。 這些答案大約有10年歷史了。 我想知道今天是否仍然是一個很好的解決方案,或者還有更多新的庫
您可以使用defaultdict
或者,如果要使用常規dict,則可以使用setdefault()
方法。
使用defaultdict
:
from collections import defaultdict
mydict = defaultdict(list) # new key is initialized with an empty list
mydict[key].append(value) # so it is always safe to append
使用setdefault()
:
mydict = {}
mydict.setdefault(key, []).append(value)
哪一種都不應該是線程安全的IIRC,即使它們看起來不是那樣:方法實現是用C語言編寫的,因此不能被Python代碼打斷。 因此,例如,永遠不可能讓兩個setdefault()
方法在字面上同時執行並引起競爭條件。
通常首選defaultdict
,因為它性能更高,僅在需要時才創建空列表,並且生成的代碼更簡單。 如果字典中的某些鍵可能具有非列表值,則setdefault()
版本可能會更好。
Python的指令對單個操作是安全的,但對多個操作則不安全。 您當前正在執行的是多項操作。 鎖很好,通常是處理此問題的標准方法。
看一下這里,以了解有關Python線程安全性的一些詳細信息。
http://effbot.org/pyfaq/what-kinds-of-global-value-mutation-are-thread-safe.htm
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.