有两种懒汉和饿汉:
饿汉:饿了就饥不择⻝了,所以在单例类定义的时候就进⾏实例化。
懒汉:顾名思义,不到万不得已就不会去实例化类,也就是在第⼀次⽤到的类实例的时候才会 去实例化。
饿汉模式(线程安全):
在最开始的时候静态对象就已经创建完成,设计⽅法是类中包含⼀个静态成员指针,该指针指 向该类的⼀个对象,提供⼀个公有的静态成员⽅法,返回该对象指针,为了使得对象唯⼀,构造函数设为私有。
#include <iostream>
#include <algorithm>
using namespace std;
class SingleInstance {
public:
static SingleInstance* GetInstance() {
static SingleInstance ins;
return &ins;
}
~SingleInstance(){};
private:
//涉及到创建对象的函数都设置为private
SingleInstance() { std::cout<<"SingleInstance() 饿汉"<<std::endl;
}
SingleInstance(const SingleInstance& other) {};
SingleInstance& operator=(const SingleInstance& other) {return
*this;}
};
int main(){
//因为不能创建对象所以通过静态成员函数的⽅法返回静态成员变量
SingleInstance* ins = SingleInstance::GetInstance();
return 0;
}
//输出 SingleInstance() 饿汉
懒汉模式(线程安全需要加锁):
尽可能的晚的创建这个对象的实例,即在单例类第⼀次被引⽤的时候就将⾃⼰初始化, C++ 很多地⽅都有类型的思想,⽐如写时拷⻉,晚绑定等。
#include <pthread.h>
#include <iostream>
#include <algorithm>
using namespace std;
class SingleInstance {
public:
static SingleInstance* GetInstance() {
if (ins == nullptr) {
pthread_mutex_lock(&mutex);
if (ins == nullptr) {
ins = new SingleInstance();
}
pthread_mutex_unlock(&mutex);
}
return ins;
}
~SingleInstance(){};
//互斥锁
static pthread_mutex_t mutex;
private:
//涉及到创建对象的函数都设置为private
SingleInstance() { std::cout<<"SingleInstance() 懒汉"<<std::endl;
}
SingleInstance(const SingleInstance& other) {};
SingleInstance& operator=(const SingleInstance& other) { return
*this; }
//静态成员
static SingleInstance* ins;
};
//懒汉式 静态变量需要定义
SingleInstance* SingleInstance::ins = nullptr;
pthread_mutex_t SingleInstance::mutex;
int main(){
//因为不能创建对象所以通过静态成员函数的⽅法返回静态成员变量
SingleInstance* ins = SingleInstance::GetInstance();
delete ins;
return 0;
}
//输出 SingleInstance() 懒汉
单例模式的适⽤场景
(1)系统只需要⼀个实例对象,或者考虑到资源消耗的太⼤⽽只允许创建⼀个对象。
(2)客户调⽤类的单个实例只允许使⽤⼀个公共访问点,除了该访问点之外不允许通过其它 ⽅式访问该实例(就是共有的静态⽅法)。