http://blog.csdn.net/windboyzsj/article/details/2790485ios
最近接触的一个项目要用到单件模式,我像往常同样哒哒(敲击键盘ing)一个单件模式的典型结构很快就出如今个人面前: c++
- class Singleton
- {
- public:
- ~Singleton(){}
- static Singleton* Instance()
- {
- if (_instance == NULL)
- {
- _instance = new Singleton();
- }
- return _instance;
- }
- private:
- Singleton(){}
- static Singleton* _instance;
- };
- Singleton* Singleton::_instance = NULL;
不知道为何,此次忽然以为new这个单词太耀眼了,熟悉c++的程序员都知道,有new就离不开delete,既然单件模式共用一个实例,那么这个实例何时释放呢。带着好奇我在它的析构函数加了个打印语句,但因为new操做是在堆里分配内存,估计它的析构函数不会被调用,而试验结果确实如此。这样一来那单件模式的析构函数不是彻底废了吗,若是这个单件类还有指针成员用new分配了空间那又应该在哪里释放?单件的实例又应该如何释放。固然,咱们能够在程序退出时经过 delete Singleton::Instance(); 来释放内存并触发析构函数。但这样一来,写好的类给别人用时就要叮嘱别人,用完后必定要释放- - !,再说别人不必定记得...有没有一种机制让单件模式自动释放?百度,google好久,发现关注这个问题的寥寥无几,但仍是给我找到了一篇文章让我再次领略C++的灵活。按此文章大概把代码修改以下; 程序员
- class Singleton
- {
- public:
- ~Singleton(){}
- static Singleton* Instance()
- {
- if (_instance == NULL)
- {
- _instance = new Singleton();
- }
- return _instance;
- }
- private:
- Singleton(){}
- static Singleton* _instance;
- class Cleaner
- {
- public:
- Cleaner(){}
- ~Cleaner()
- {
- if(Singleton::Instance())
- delete Singleton::Instance();
- }
- };
- static Cleaner clr;
- };
- Singleton* Singleton::_instance = NULL;
事先声明我用VC6.0编译上面的代码(固然我有加一些测试代码)发现,clr并无实例化,固然也就是没有析构了,暂时不清楚为何,但这里的设计倒是很值得品味。它经过一个内嵌类和一个静态成员来实现了自动释放的机制,至关于为单件加了个垃圾回收器。整个设计最巧妙的地方在于static Cleaner clr;这个声明,因为是静态成员,系统会在栈里分配内存,回收工做也就由系统自动完成了。这个思路另我想起了经过静态变量来实现类的静态构造函数,他们都有殊途同归之处。至于私有的内嵌类主要是防止单件类的专用垃圾筒被打扰...
虽然上面代码没有达到目的,但根据他的思路,能够作一下调整,把Cleaner的实例化延迟,下面贴出整个测试代码,一下代码在VC6编译经过。 函数
- #include <iostream.h>
- class Singleton
- {
- public:
- ~Singleton(){cout<<"singleton deconstruct"<<endl;}
- static Singleton* Instance()
- {
- if (_instance == NULL)
- {
- _instance = new Singleton();
- static Cleaner cl;
- }
- return _instance;
- }
- void Print(char* str)
- {
- cout<<"singleton print:"<<str<<endl;
- }
- private:
- Singleton(){cout<<"singleton construct"<<endl;}
- static Singleton* _instance;
- class Cleaner
- {
- public:
- Cleaner(){cout<<"cleaner construct"<<endl;}
- ~Cleaner()
- {
- cout<<"cleaner deconstruct"<<endl;
- if(Singleton::Instance())
- delete Singleton::Instance();
- }
- };
- };
- Singleton* Singleton::_instance = NULL;
- int main(int argc, char* argv[])
- {
- Singleton::Instance()->Print("print 1");
- Singleton::Instance()->Print("print 2");
- return 0;
- }