- 懒汉:故名思义,不到万不得已就不会去实例化类,也就是说在第一次用到类实例的时候才会去实例化,所以上边的经典方法被归为懒汉实现;
- 饿汉:饿了肯定要饥不择食。所以在单例类定义的时候就进行实例化。
一个类只能实例化一个对象,所以一定要用静态
class
singleton
{
protected
:
//构造函数声明为private或protect防止被外部函数实例化
singleton(){}
private
:
static
singleton* p = NULL;
public
:
static
singleton* instance(){
if
(p == NULL)
p =
new
singleton();
return
p;
}
};
这是一个很棒的实现,简单易懂。
但这是一个完美的实现吗?不!单线程是完美的
该方法是线程不安全的,考虑两个线程同时首次调用instance方法且同时检测到p是NULL值,则两个线程会同时构造一个实例给p,这是严重的错误!
同时,这也不是单例的唯一实现!
懒汉模式 加锁
- class Singleton
- {
- private:
- static Singleton* m_instance;
- Singleton(){}
- public:
- static Singleton* getInstance();
- };
- Singleton* Singleton::getInstance()
- {
- if(NULL == m_instance)
- {
- Lock();//借用其它类来实现,如boost
- if(NULL == m_instance)
- {
- m_instance = new Singleton;
- }
- UnLock();
- }
- return m_instance;
- }
饿汉模式
class
singleton
{
protected
:
//构造函数声明为private或protect防止被外部函数实例化
singleton(){}
private
:
static
singleton* p = new
singleton
;
public
:
static
singleton* instance(){
return
p;
}
};
是不是特别简单呢?
以空间换时间,你说简单不简单?
面试的时候,线程安全的单例模式怎么写?肯定怎么简单怎么写呀!饿汉模式反而最懒[正经脸]!