2010-01-31 315 views
13

Suppoes我:什麼操作在std :: map上是線程安全的?

stl::map<std::string, Foo> myMap; 

是下面的函數線程安全的?

myMap["xyz"] ? 

即,我想擁有這個在許多線程之間共享的巨型只讀地圖;但我不知道是否即使搜索它也是線程安全的。

謝謝!

編輯:

一切都寫入一次第一。

然後,多線程讀取它。

我試圖避免鎖使盡可能的儘可能多。 (我知道yaya可能過早優化)

回答

11

理論上沒有STL容器是線程安全的。在實踐中,如果容器未被同時修改,閱讀是安全的。即該標準沒有規定關於線程的規定。標準的下一個版本將和IIUC一起保證安全的只讀行爲。

如果您真的擔心,請使用二進制搜索的排序數組。

2

STL集合不是線程安全的,但是爲一個線程安全添加相當簡單。

最好的辦法是圍繞相關集合創建一個線程安全包裝。

6

至少在Microsoft的實現中,從容器中讀取是線程安全的(reference)。

但是,std::map::operator[]可以修改數據並且未聲明const。你應該使用std::map::find,這是const,得到一個const_iterator並取消它。

+0

爲了在容器中有任何東西,它需要被寫入。因此,線程安全問題... – 2010-01-31 04:51:19

+1

這些問題指定我們正在查看只讀地圖。我認爲這意味着它在從多個線程讀取之前完全填充到一個線程中。 – 2010-01-31 05:24:12

4

從理論上講,只讀數據結構和函數不需要任何鎖定用於線程安全。它本質上是線程安全的。有沒有數據競爭併發內存讀取。但是,只能通過一個線程來保證安全的初始化。

正如Max S.指出的,大多數讀取地圖中元素的實現(如myMap["xyz"])都沒有寫入操作。如果是這樣,那麼它是安全的。但是,再一次,你必須保證除初始化階段外沒有線程修改結構。

7

C++ 11要求聲明爲const的所有成員函數對於多個讀取器都是線程安全的。

調用myMap["xyz"]不是線程安全的,因爲std::map::operator[]未聲明爲const。 雖然呼叫myMap.at("xyz")是線程安全的,因爲std::map::at被聲明爲const

相關問題