单例模式

【1】什么是单例模式?

单例,即所谓,单个实例。换句话说,类的对象也需要“计划生育”政策。

单例模式即在应用程序中一个类有且仅有一个实例的一种设计模式。

单例模式保证系统中一个类只有一个实例且该实例易于外界访问,从而方便对实例个数的控制并节约系统资源。

结合以上需求、编程经验,不难总结单例模式要点有三:

一、某个类只能有一个实例。代码体现在构造函数访问属性为私有private,外界不可调用。另外,赋值操作也应该私有。

二、必须自行创建这个实例。既然有要点一private的约束,那么,实例肯定得自给自足。

三、必须自行向整个应用程序系统提供这个实例。为了便于外界访问,结合一二、这个供访问的接口设计为静态static成员函数。

【2】单例模式的代码示例:

示例代码:

复制代码
 1 #include <iostream>
 2 using namespace std;
 3 
 4 class Singleton
 5 {
 6 public:
 7     static Singleton *getInstance()
 8     {
 9         return m_pInstance;
10     }
11     void show()
12     {
13         cout << m_nValue << endl;
14     }
15 
16 private:
17     int m_nValue;
18     static Singleton *m_pInstance;
19     Singleton(int value) : m_nValue(value)
20     {}
21 };
22 
23 Singleton* Singleton::m_pInstance = new Singleton(8899);
24 
25 class A : public Singleton
26 {
27 
28 };
29 
30 void main()
31 {
32     Singleton *pObj1 = Singleton::getInstance();
33     Singleton *pObj2 = A::getInstance();
34     cout << pObj1 << endl;
35     cout << pObj2 << endl;
36     pObj1->show();
37     pObj2->show();
38     cout << (pObj1 == pObj2) << endl;
39     system("pause");
40 }
41 
42 // run result:
43 /*
44 004583F0
45 004583F0
46 8899
47 8899
48 1
49 请按任意键继续. . .
50 */
复制代码

【3】单例模式的进化史

(1)代码1:

说明:饿汉式

复制代码
 1 class CSingleton
 2 {
 3 private:
 4     CSingleton()   // 构造函数是私有的
 5     {
 6     }
 7     static CSingleton *m_pInstance;
 8 
 9 public:
10     static CSingleton *GetInstance()
11     {
12         return m_pInstance;
13     }
14 };
15 
16 CSingleton *CSingleton::m_pInstance = new CSingleton();
复制代码

(2)代码2:

说明:懒汉式

复制代码
 1 class CSingleton
 2 {
 3 private:
 4     CSingleton()   // 构造函数是私有的
 5     {}
 6     static CSingleton *m_pInstance;
 7 
 8 public:
 9     static CSingleton *GetInstance()
10     {
11         if (NULL == m_pInstance)  // 判断是否第一次调用
12         {
13             m_pInstance = new CSingleton();
14         }
15         return m_pInstance;
16     }
17 };
18 
19 CSingleton *CSingleton::m_pInstance = NULL;
复制代码

(3)代码3:

说明:静态对象引用返回式

复制代码
 1 class CSingleton
 2 {
 3 private:
 4     CSingleton()   // 构造函数是私有的
 5     {}
 6 
 7 public:
 8     static CSingleton & GetInstance()
 9     {
10         static CSingleton instance;   // 局部静态对象
11         return instance;
12     }
13 };
复制代码

(4)代码4:

说明:静态对象指针返回式

复制代码
 1 class CSingleton
 2 {
 3 private:
 4     CSingleton()   // 构造函数是私有的
 5     {}
 6 
 7 public:
 8     static CSingleton * GetInstance()
 9     {
10         static CSingleton instance;   // 局部静态对象
11         return &instance;
12     }
13 };
复制代码

(5)代码5:

说明:静态对象引用返回式优化(禁止拷贝构造和赋值)

复制代码
 1 class CSingleton
 2 {
 3 private:
 4     CSingleton()   // 构造函数是私有的
 5     {
 6     }
 7     CSingleton(const CSingleton &);
 8     CSingleton & operator = (const CSingleton &);
 9 
10 public:
11     static CSingleton & GetInstance()
12     {
13         static CSingleton instance;   // 局部静态对象
14         return instance;
15     }
16 };
复制代码

(6)代码6:

说明:线程安全式单例类

复制代码
 1 struct CCriticalSection
 2 {
 3     void Lock()
 4     {}
 5     void UnLock()
 6     {}
 7 };
 8 
 9 class Lock
10 {
11 private:       
12     CCriticalSection m_cs;
13 
14 public:
15     Lock(CCriticalSection  cs) : m_cs(cs)
16     {
17         m_cs.Lock();
18     }
19     ~Lock()
20     {
21         m_cs.UnLock();
22     }
23 };
24 
25 class Singleton
26 {
27 private:
28     Singleton();
29     Singleton(const Singleton &);
30     Singleton& operator = (const Singleton &);
31 
32 public:
33     static Singleton *Instantialize();
34     static Singleton *pInstance;
35     static CCriticalSection cs;
36 };
37 
38 Singleton* Singleton::pInstance = NULL;
39 
40 Singleton::Singleton()
41 {}
42 
43 Singleton* Singleton::Instantialize()
44 {
45     if (NULL == pInstance)
46     {   // double check
47         Lock lock(cs);           // 用lock实现线程安全,用资源管理类,实现异常安全
48         // 使用资源管理类,在抛出异常的时候,资源管理类对象会被析构,析构总是发生的无论是因为异常抛出还是语句块结束。
49         if (NULL == pInstance)
50         {
51             pInstance = new Singleton();
52         }
53     }
54     return pInstance;
55 }
复制代码

 

Good Good Study, Day Day Up.

顺序 选择 循环 总结

posted @   kaizenly  阅读(466)  评论(0编辑  收藏  举报
编辑推荐:
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· AI与.NET技术实操系列:向量存储与相似性搜索在 .NET 中的实现
· 基于Microsoft.Extensions.AI核心库实现RAG应用
· Linux系列:如何用heaptrack跟踪.NET程序的非托管内存泄露
· 开发者必知的日志记录最佳实践
阅读排行:
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· Manus的开源复刻OpenManus初探
· AI 智能体引爆开源社区「GitHub 热点速览」
· C#/.NET/.NET Core技术前沿周刊 | 第 29 期(2025年3.1-3.9)
· 从HTTP原因短语缺失研究HTTP/2和HTTP/3的设计差异
历史上的今天:
2013-09-01 [5] 智能指针boost::shared_ptr
2013-09-01 [4] 智能指针boost::scoped_ptr
打赏

喜欢请打赏

扫描二维码打赏

微信打赏

点击右上角即可分享
微信分享提示