zoukankan      html  css  js  c++  java
  • C++: 单例模式和缺陷

    C++: 单例模式和缺陷

    实现一个单例模式

    1 class Singleton {
    2     private:
    3         Singleton() { cout << "Singleton::constructor" << endl; }
    4         ~Singlton() { cout << "Singleton::destructor" << endl; }
    5         Singleton(const Singleton&) {};
    6         Singleton &operator=(const Singleton&) {};
    7     public:
    8         static Singleton* getInstance() {
    9             if(m_aInstance == NULL) {
    10                 m_aInstance = new Singleton();
    11             }
    12             return m_aInstance;
    13         }
    14         void show() {
    15             cout << "Singleton::show" << endl;
    16         }
    17     private:
    18         static Singleton* m_aInstance;
    19 };
    20  
    21 Singleton* Singleton::m_aInstance = NULL;
    22  
    23 int main(int argc, char **argv) {
    24     Singleton* aSingleton = Singleton::getInstance();
    25     aSingleton->show();
    26     return 0;
    27 }
    编译执行上面的代码,输出如下:
    Singleton::constructor
    Singleton::show
    
    我们发现上面的输出并没有调用到Singleton的虚构函数,Singleton的资源可能没有被释放。现在的问题是要怎么才能在程序退出的时候正确释放Singleton的资源。我们注意到这样一个事实:
    系统会自动调用在栈和静态数据区上分配的对象的析构函数来释放资源。
    

    修改程序如下:

    1 class Singleton {
    2     private:
    3         Singleton() { cout << "Singleton::constructor" << endl; }
    4         ~Singleton() { cout << "Singleton::destructor" << endl; }
    5         Singleton(const Singleton&) {};
    6         Singleton &operator=(const Singleton&) {};
    7     public:
    8         static Singleton* getInstance() {
    9             if(m_aInstance == NULL) {
    10                 m_aInstance = new Singleton();
    11             }
    12             return m_aInstance;
    13         }
    14         void show() {
    15             cout << "Singleton::show" << endl;
    16         }
    17  
    18     private:
    19         class Garbage{
    20             public:
    21                 ~Garbage() {
    22                     if(m_aInstance != NULL) {
    23                         delete m_aInstance;
    24                     }
    25                 }
    26         };
    27      
    28     private:
    29         static Singleton* m_aInstance;
    30         static Garbage m_garbage;
    31 };
    32  
    33 Singleton* Singleton::m_aInstance = NULL;
    34 Singleton::Garbage Singleton::m_garbage;
    35  
    36 int main(int argc, char **argv) {
    37     Singleton* aSingleton = Singleton::getInstance();
    38     aSingleton->show();
    39     return 0;
    40 }
    编译上面的代码并执行,输出如下:
    Singleton::constructor
    Singleton::show
    Singleton::destructor
    

    我们看到Singleton::destructor被明确的执行了。

  • 相关阅读:
    BZOJ 4769: 超级贞鱼 逆序对 + 归并排序
    BZOJ 4897: [Thu Summer Camp2016]成绩单 动态规划
    luogu 4059 [Code+#1]找爸爸 动态规划
    CF718C Sasha and Array 线段树 + 矩阵乘法
    计蒜客 2238 礼物 期望 + 线段树 + 归并
    BZOJ 2157: 旅游 (结构体存变量)
    BZOJ 3786: 星系探索 ETT
    BZOJ 3545: [ONTAK2010]Peaks 启发式合并 + 离线 + Splay
    Spring的几种初始化和销毁方法
    SpringCloud之Zuul高并发情况下接口限流(十二)
  • 原文地址:https://www.cnblogs.com/lidabo/p/3701101.html
Copyright © 2011-2022 走看看