转载自: https://www.cnblogs.com/chengjundu/p/8473564.html
设计模式及c++实现强烈安利这个网站:https://sourcemaking.com/design_patterns/abstract_factory/cpp/2
0.概述
单例模式顾名思义,保证一个类仅可以有一个实例化对象,并且提供一个可以访问它的全局接口。实现单例模式必须注意一下几点:
单例类只能由一个实例化对象。
单例类必须自己提供一个实例化对象。
单例类必须提供一个可以访问唯一实例化对象的接口。
单例模式分为懒汉和饿汉两种实现方式。
1.懒汉单例模式
懒汉:故名思义,不到万不得已就不会去实例化类,也就是说在第一次用到类实例的时候才会去实例化一个对象。
在访问量较小,甚至可能不会去访问的情况下,采用懒汉实现,这是以时间换空间。
1.1 非线程安全的懒汉单例模式
关键代码:构造函数是私有的,不能通过赋值运算,拷贝构造等方式实例化对象。
//懒汉式一般实现:非线程安全,getInstance返回的实例指针需要delete
class Singleton
{
public:
static Singleton* getInstance();
~Singleton(){}
private:
Singleton(){} //构造函数私有
Singleton(const Singleton& obj) = delete; //明确拒绝拷贝构造
Singleton& operator=(const Singleton& obj) = delete; //明确拒绝赋值操作
static Singleton* m_pSingleton; //静态对象指针
};
Singleton* Singleton::m_pSingleton = NULL; //懒汉模式。不在定义的时候实例化
Singleton* Singleton::getInstance()
{
if(m_pSingleton == NULL) //懒汉模式。在需要的时候实例化
{
m_pSingleton = new Singleton;
}
return m_pSingleton;
}
1.2 线程安全的懒汉单例模式
std::mutex mt;
class Singleton
{
public:
static Singleton* getInstance();
private:
Singleton(){} //构造函数私有
Singleton(const Singleton&) = delete; //明确拒绝
Singleton& operator=(const Singleton&) = delete; //明确拒绝
static Singleton* m_pSingleton; //静态对象指针
};
Singleton* Singleton::m_pSingleton = NULL; //懒汉模式。不在定义的时候实例化
Singleton* Singleton::getInstance()
{
if(m_pSingleton == NULL)
{
mt.lock();
if(m_pSingleton == NULL) //懒汉模式。在需要的时候实例化
{
m_pSingleton = new Singleton();
}
mt.unlock();
}
return m_pSingleton;
}
1.3 返回一个reference指向local static对象
class Singleton
{
public:
static Singleton& getInstance();
private:
Singleton(){}
Singleton(const Singleton&) = delete; //明确拒绝
Singleton& operator=(const Singleton&) = delete; //明确拒绝
};
Singleton& Singleton::getInstance()
{
static Singleton singleton;
return singleton;
}
2.饿汉单例模式
饿汉:饿了肯定要饥不择食。所以在单例类定义的时候就进行实例化。
在访问量比较大,或者可能访问的线程比较多时,采用饿汉实现,可以实现更好的性能。
这是以空间换时间。
//饿汉式:线程安全,注意一定要在合适的地方去delete它
class Singleton
{
public:
static Singleton* getInstance();
private:
Singleton(){} //构造函数私有
Singleton(const Singleton&) = delete; //明确拒绝
Singleton& operator=(const Singleton&) = delete; //明确拒绝
static Singleton* m_pSingleton; //静态对象指针
};
Singleton* Singleton::m_pSingleton = new Singleton();//定义时直接实例化
Singleton* Singleton::getInstance()
{
return m_pSingleton;
}