C++ and Singleton
在单线程模式下,最简单的办法就是只能通过一个method获取instance,在第一次access的时候建立instance
class Singleton {
public:
static Singleton& instance() {
static Singleton instance_;
return instance_;
}
}
但是这个不是thread-safe的,对于if (constructed == false) 是存在race-condition的 那怎么办?加锁咯
Singleton* Singleton::instance() {
Lock lock;
if (pInstance == 0) {
pInstance = new Singleton;
}
return pInstance;
}
这个solution的问题是expensive. 每次access都需要acquire lock. 现实中,我们只需要在初始化的时候加锁。
著名的double checking locking pattern
Singleton* Singleton::instance() {
if (pInstance == 0) {
Lock lock
if (pInstance == 0) {
pInstance = new Singleton;
}
}
return pInstance;
}
DCLP也不行啊,因为
Step 1: Allocate memory to hold a Singleton object. Step 2: Construct a Singleton object in the allocated memory. Step 3: Make pInstance point to the allocated memory.
这三步有可能不是顺序的,#2 #3compiler优化可能会swap,使得DCLP完全没用
C++11之后
If control enters the declaration concurrently while the variable is being initialized, the concurrent execution shall wait for completion of the initialization.
所以不用再overengineeering了
public:
static Singleton& get(){
static Singleton instance;
return instance;
}
Singleton(Singleton const&) = delete; //no copy & assigment constructor
void operator=(Singleton const&) = delete;
private:
Singleton() {}
Written on November 30, 2016