2015-01-06 47 views
1

我所經歷的一些問題,我的原子容器,看見this linkC++ 11的std線程安全::原子<T>拷貝構造函數

是有一個原因的std ::原子不復制施工的?解決方案似乎是this他們只是通過T值與原子加載函數的非原子構造函數(如果我沒有弄錯)。

所以一般來說,這是拷貝構造線程安全的?

template<typename T> 
struct MobileAtomic 
{ 
    std::atomic<T> atomic; 

    explicit MobileAtomic(std::atomic<T> const& a) : atomic(a.load()) {} 

}; 
+0

目前還不清楚這個代碼是否能夠實現任何明智的。 Atomics服務於一個非常特定的目的,通常複製它們是沒有意義的。 –

+1

作爲一個比喻:一個原子int比一個整數更接近互斥或信號量。您可能想要查詢信號量的當前狀態(對應於原子加載),但複製信號量本身沒有意義。這是一個同步機制,如果不合理,則複製一份。 –

+2

我也不清楚這對於「構造函數是線程安全的」意味着什麼。誰在共同構建什麼? –

回答

4

有一個原因的std ::原子不復制施工的?

當您要求複製可構造atomic時,您需要將單線順序一致性的「正常」規則應用於不遵循這些規則的變量。

從本質上說,不存在通用的解決方案。

通過使用你的問題表明的構造,你犧牲在一個確定的結果,你有沒有保證,建設完成後的源和目標對象是相等的。

+0

在我看來,我只有兩個選擇:我只能通過值返回原子變量的值(可能會由另一個線程更改,直到值由caller = race分配),或返回對原子變量的引用(這是我不想公開的變量)。我想我最好的選擇是返回一個我還沒有嘗試過的const引用。 – JohnJohn

+0

@JohnJohn另一種選擇是在讀取期間用變量鎖定變量。 –

+1

@JohnJohn:你可能沒有意識到它,但是**一旦你做了一個副本**,原始對象的值就可能偏離副本的值。這不是一個競爭條件。這是您有兩個變量時的正常行爲。如果你邏輯上有一個值,你應該有一個對象。 – MSalters