细说Singleton模式3.pptVIP

  • 0
  • 0
  • 约2.57千字
  • 约 10页
  • 2017-06-02 发布于河南
  • 举报
细说Singleton模式3

细说Singleton模式 创建、多线程与销毁 3.Singleton销毁   在这里,我们就到了Singleton最简单也最复杂的地方了。   为什么说它简单?我们根本可以不理睬创建的对象m_pInstance的销毁啊。因为虽然我们一直没有将Singleton对象删除,但不会造成内存泄漏。为什么这样说呢?因为只有当你分配了累积行数据并丢失了对他的所有reference是,内存泄漏才发生。而对Singleton并不属于上面的情况,没有累积性的东东,而且直到结束我们还有它的引用。在现代操作系统中,当一个进程结束后,将自动将该进程所有内存空间完全释放。(可以参考《effective C++》条款10,里面讲述了内存泄漏)。   但有时泄漏还是存在的,那是什么呢?就是资源泄漏。比如说如果该Singleton对象管理的是网络连接,OS互斥量,进程通信的handles等等。这时我们就必须考虑到Singleton的销毁了。谈到销毁,那可是一个复杂的课题(两天三夜也说不完^_^ 开玩笑的啦,大家轻松一下嘛)。 我们需要在恰当的地点,恰当的时机删除Singleton对象,并且还要在恰当的时机创建或者重新创建Singleton对象。   在我们的“解二”中,在程序结束时会自动调用Singleton的析构函数,那么也将自动释放所获取的资源。在大多数情况下,它都能够有效运作。那特殊情况是什么呢?   我们以KDL(keyboard,display,log)模型为例,其中K,D,L均使用Singleton模式。只要keyboard或者display出现异常,我们就必须调用log将其写入日志中,否则log对象不应该创建。对后面一条,我们的Singleton创建时就可以满足。 在前面我们已经说到,在产生一个对象时(非用new产生的对象),由编译器自动调用了atexit(__DestroyObject)函数来实现该对象的析构操作。而C++对象析构是LIFO进行的,即先产生的对象后摧毁。   如果在一般情况下调用了log对象,然后开始销毁对象。按照“后创建的先销毁”原则:log对象将被销毁,然后display对象开始销毁。此时display在销毁发现出现异常,于是调用log对象进行记录。但事实上,log对象已经被销毁,那么调用log对象将产生不可预期的后果,此问题我们称为Dead Reference。所以前面的解决方案不能解决目前我们遇到的问题。   Andrei Alexandrescu提出了解决方案,称为Phoenix Singleton(取自凤凰涅磐典故) 88./*解四*/   89.class Singleton   90.{   91.public:   92.static Singleton Instance(){   93.if( !m_pInstatnce){   94.Lock(m_mutex)   95.If( !m_pInstance ){   96.if(m_destroyed)   97.OnDeadReference(); 98.else   99.Create();   100.}   101.UnLock(m_mutex);   102.}   103.return *m_pInstance;   104.}   105.private:   106.static volatitle Singleton *m_pInstatnce; 107.static bool m_destroyed;   108.private:   109.Singleton();   110.Singleton(const Singleton);   111.Singleton operator=(const Singleton);   112.~Singleton(){   113.m_pInstance = 0; 114.m_destroyed = true;   115.}   116.static void Create(){   117.static Singleton sInstance;   118.m_pInstanace = sInstance;   119.}   120.static void OnDeadReference(){   121.Create();  122.new (m_pInstance) Singleton;   123.atexit(KillPhoenixSingleton);   124.m_destroyed = false;   125.}   126.void KillPhoenixSingleton(){   127.m_pInstance-~Singleton();   128.}   12

文档评论(0)

1亿VIP精品文档

相关文档