suncode

  博客园 :: 首页 :: 新随笔 :: :: :: 管理 ::

意图:保证一个类仅有一个实例,并提供一个访问的全局访问点

--------------------singleton.h-----------------------

View Code
#ifndef SINGLETON_H
#define SINGLETON_H

class singleton
{
public:
  
static singleton* instance();
protected:
  singleton();
private:
  
static singleton* _instance;
};


#endif //SINGLETON_H

---------------------singleton.cpp----------------------

View Code
#include "singleton.h"
singleton
* singleton::_instance=0;
singleton
* singleton::instance()
{
  
if (_instance==0)
  {
     _instance
=new singleton;
  }
  
return _instance;
}

singleton::singleton()
{
}

int main()
{
   singleton
*tmp=singleton::instance();
  singleton
*tmp2=singleton::instance();
}

1,多线程问题: 
单件的通常设计成在获取对象实例的时候才创建(方便使用),但是在多线程的环境下,可能同一时刻多个线程调用获取实例方法,所以,如果保护不好很容易造成不在单件了,而是生成了很多个事例。所以单件事例在创建的时候需要加琐保护。 由于加琐会增加获取单件实例的运行负荷,所以通常我们需要对加琐进行优化。 琐的优化通常就是常听说的双检测锁的方式; 

2,资源释放问题: 
由于单件实例往往使用了静态数据,通常是个静态指针,而且提供一个静态的方法来获取/生成实例。这个实例通常是new出来的,使用这个实例的对象可能有很多个,于是问题来了: 这个单件实例应该如何释放呢? 

能想到的可能会有下面几种方法: 
1)采用引用记数,让单件的获取方,获取后自己释放;这个方法避免不了反复创建和释放单件实例,而且某一个使用者忘记释放,单件实例就再也释放不了了。 
2)由一个模块负责释放单件实例,但是一旦这个模块在进程中加载多份,就又变得麻烦了,模块的销毁有先后顺序,前一个模块将单件释放了,但是后一个不知道单件已经“挂”了,如果这种场景在多线程情况下,会是什么样子,就很难说了。 

参考代码:

View Code
templage <typename T>
class CAutoReleaser
{
private:
T
* m_MgObject; // 受管理的对象
public:
CAutoReleaser() : m_MgObject(NULL)
{
}
virtual ~CAutoReleaser()
{
delete m_MgObject;
}
void manage(T* pObj)
{
this-> m_MgObject = pObj;
return;
}
};

class SG
{
private:
static SG* m_pInstance;
static CAutoReleaser <SG> m_autoreleaser;
SG(){}
~SG(){}
public:
static SG* getInstance()
{
if (NULL == m_pInstance)
{
SG
* pnewSG = new SG;
if (pnewSG)
{
m_pInstance
= pnewSG;
m_autoreleaser.manage(pnewSG);
}
}
return m_pInstance;
}
};


posted on 2011-03-29 14:46  suncode  阅读(339)  评论(0)    收藏  举报