C++之单例(singleton)模式

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了C++之单例(singleton)模式相关的知识,希望对你有一定的参考价值。


0. 简介

有时候我们在面对通用代码时候,经常会尝试着创建多个示例函数来对一个函数多次赋值,这样会损耗很多的内存空间,这对于代码来说是不利的。而单例模式可以很好的解决这个问题。但是实现一个实用的单例模式来说,这个并不容易。

1. 单例函数

1.1 饿汉模式

饿汉模式 是指单例实例在类装载时就构建,并被立即执行初始化:

public class Test 
private Test()

public static Test instance = new Test();// 直接对Test构造函数进行实例化
public Test getInstance()
return instance;

优点
1.线程安全
2.在类加载的同时已经创建好一个静态对象,调用时反应速度快
缺点
资源效率不高,可能​​​getInstance()​​​永远不会执行到,但执行该类的其他静态方法或者加载了该类​​(class.forName)​​,那么这个实例仍然初始化 。如果类是多态的, 那静态成员变量初始化顺序还是没保证,下面我们将详细解释这个问题.

例如:有两个单例模式的类 ​​ASingleton​​​ 和 ​​BSingleton​​​, 某天你想在 ​​BSingleton​​​ 的构造函数中使用 ​​ASingleton​​​ 实例, 这就出问题了. 因为 ​​BSingleton m_pInstance​​​ 静态对象可能先 ​​ASingleton​​​ 一步调用初始化构造函数, 结果 ​​ASingleton::getInstance()​​ 返回的就是一个未初始化的内存区域, 程序还没跑就直接崩掉.

1.2 懒汉模式

懒汉式是指:单例实例在第一次被使用时构建,但延迟初始化:

class Test 
private Test()

public static Test instance = null;
public static Test getInstance()
if (instance == null)
//多个线程判断instance都为null时,在执行new操作时多线程会出现重复情况
instance = new Test();

return instance;

优点:
避免了饿汉式的那种在没有用到的情况下创建事例,资源利用率高,不执行getInstance()就不会被实例,可以执行该类的其他静态方法。
缺点:
懒汉式在单个线程中没有问题,但多个线程同事访问的时候就可能同事创建多个实例,而且这多个实例不是同一个对象,虽然后面创建的实例会覆盖先创建的实例,但是还是会存在拿到不同对象的情况。解决这个问题的办法就是加锁​​synchonized​​,第一次加载时不够快,多线程使用不必要的同步开销大。

1.3 双重模式

class Test 
private Test()

public static Test instance = null;

public static Test getInstance()
if (instance == null)
synchronized (Test.class)
if (instance == null)
instance = new Test();



return instance;

优点
资源利用率高,不执行getInstance()就不被实例,可以执行该类其他静态方法
缺点
第一次加载时反应不快

1.4 静态内部类

class Test 
private Test()


private static class SingletonHelp
static Test instance = new Test();


public static Test getInstance()
return SingletonHelp.instance;

优点
资源利用率高,不执行getInstance()不被实例,可以执行该类其他静态方法
缺点
第一次加载时反应不够快

1.5 总结:

一般采用饿汉式,若对资源十分在意可以采用静态内部类,不建议采用懒汉式及双重检测 。

2 . 设计一款完美的单例模式

这里我们选择静态内部类+模板类的组合方法来有效的对多线程程序进行单例模式设计

2.1 Best Practices

网络上存在一些简单的单例模式方法,这里先对一种简单的易懂的单例模式进行解释:

#include <iostream>
#include <cassert>

class Singleton

public:
static Singleton& Instance()

static Singleton instance; // 静态实例化:
return instance;

public:
Singleton(const Singleton&) = delete;
Singleton(Singleton&&) = delete;
Singleton& operator=(const Singleton&) = delete;
Singleton& operator=(Singleton&&) = delete;
private:
Singleton() = default;
~Singleton() = default;
;

int main()

auto& a = Singleton::Instance(); //实例化
auto& b = Singleton::Instance();
assert(&a == &b);

return 0;

以上是关于C++之单例(singleton)模式的主要内容,如果未能解决你的问题,请参考以下文章

Java设计模式之单例设计模式(Singleton)

Java之单例模式(Singleton)

设计模式之单例模式——Singleton

《设计模式》之单例模式(Singleton)

初学设计模式之单例模式

Android设计模式之单例模式(Singleton Pattern)