1 本篇主要討論下多執行緒下的單例模式實現:
首先是 double check 實現方式: 這種模式可以滿足多執行緒環境下,只產生乙個例項。
templateclass但是這種實現存在除bug的隱患, 問題就在: value_ = new t; 上。《程式設計師的自我修養》上指出:dclsingleton
}return *value_;
}protected
: dclsingleton()
dclsingleton(
const dclsingleton &dcl) {}
private
:
static t*value_;
static
mutex mutex_;
};
這樣的**是有問題的,問題的**在於 cpu 的亂序執行。c++裡的new 包含了兩步。
(1)分配記憶體
(2)呼叫建構函式
所以 value_ = new t; 實際上包含了三步:
(1)分配記憶體
(2)在分配記憶體的位置上呼叫建構函式
(3)將記憶體位址賦值給 value_;
這三步中,(2), (3)兩步是可以顛倒的,也就是說,可能出現,先執行(3)這是 value_已經不為null, 當出現另乙個對getinstance的併發呼叫,if 內的 value_ != null於是返回,但是還沒有呼叫建構函式。於是使用這個指標的時候,就會導致崩潰。
這時候需要保證(2), (3)的執行順序,通常需要加上記憶體屏障,保證一定保證(2)執行完以後,再執行(3)
這裡我加上了__sync_synchronize(); 後 實現是這樣的:
static t&getinstance()這樣便可以既保證多執行緒環境安全,又保證不會出現上面的問題。}return *value_;
}
2. 加上記憶體屏障的示例**:dcl_single.h
#ifndef __dcl_single_hview code#define __dcl_single_h#include
namespace
yl ~mutex()
public
:
void
lock()
void
unlock()
private
: pthread_mutex_t mutex_;
};class
mutexguard
~mutexguard()
private
: mutex mutex_;
};template
class
dclsingleton
}return *value_;
}protected
: dclsingleton()
dclsingleton(
const dclsingleton &dcl) {}
private
:
static t*value_;
static
mutex mutex_;
};template
t* dclsingleton::value_ =null;
template
mutex dclsingleton
::mutex_;
}#endif
singletontest.cpp
#include "3. 還可以用 unix 下的 pthread_once 來實現單例模式:dcl_single.h
"#include
namespace
yl ~mgrsg()
public
:
void
print()
};}int
main(
void
)
template classmysingleton
protected
: mysingleton() {}
mysingleton(
const mysingleton&) {}
private
:
static
void
init()
private
:
static
pthread_once_t ponce_;
static t *instance;
};template
pthread_once_t mysingleton
::ponce_ =pthread_once_init;
template
t *mysingleton::instance =nullptr;
}
5. 水平有限,望及時指出錯誤。謝謝
C 之單例模式
1 c 單例模式的概念及作用 單例模式也稱為單件模式 單子模式,可能是使用最廣泛的設計模式。其意圖是保證乙個類僅有乙個例項,並提供乙個訪問它的全域性訪問點,該例項被所有程式模組共享。2 單例模式的實現原理 1 私有靜態指標變數實現 使用類的私有靜態指標變數指向類的唯一例項,並用乙個公有的靜態方法獲取...
c 多執行緒單例模式 C 設計模式之單例模式
單例模式 乙個類在記憶體中只有乙個物件 例項 並且提供乙個可以全域性訪問或者獲取這個物件的方法。這兩天學的,寫了個小例子,問了同事一些關於執行緒的問題,還有從網上查了一些資料。還犯了一些低階的錯誤。vs2017控制台輸出文字亂碼,從網上找了一些方法不管用,最後發現是自己新建專案選錯模板了,選擇了.n...
單例模式 之 單例模式 Holder
之前我寫過 單例模式中的餓漢模式和懶漢模式 他們雖然都能實現單例模式 但是優缺點很明顯 餓漢模式 不能懶載入 類載入就會被例項化 消耗很大,在併發情況下安全性很高。懶漢模式 能實現懶載入,但是在併發情況下安全性不是很高。雖然一步一步的優化,安全性得到了保證,但是卻使用了synchronized 對效...