C++工具箱——单件模版类

Posted 牧秦丶

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了C++工具箱——单件模版类相关的知识,希望对你有一定的参考价值。

我们在工作中往往会用到单件类。但是我们知道单件类的实现就那么几步,如果系统中有多个单件类的话,去一个个写非常麻烦,那么怎么办呢?


单件模版类就派上用场了:

template <typename _CoClass>
class Singleton

public:
	Singleton() 
	virtual ~Singleton() 

	static _CoClass& GetInstance()
	
		if (!m_psInstance)
		
			m_psInstance = new _CoClass();
		
		
		return *m_psInstance;
	

private:
	// 防止单件复制.
	Singleton(const Singleton& copy);
	Singleton& operator = (const Singleton& rhs);

	static _CoClass*	m_psInstance;
;


//
// 单件实例指针初始化.
//
template <typename _CoClass>
_Coclass* Singleton<_CoClass>::m_psInstance = 0;
那么该怎么用呢?如下:

class CDataMgr : public Singleton<CDataMgr>

public:
	void SaveData();
	
	// ...
;


int main()

	// ...
	CDataMgr::GetInstance().SaveData();
只要我们需要让一个类成为单件,只需从 Singleton 模版派生即可。那么我们思考下为什么这个模版类是可以工作的。


如果你熟悉 WTL的话,这个例子非常容易看懂。首先,我们知道,在C++ 中,如果定义一个指针,是不需要看见它的类型的具体实现的,我们只需要这个类型的名字就行了——这就是“前向声明”为什么可以工作的原因——其实更深层次上,一个指针在Win32平台下,内存中都为其分配4字节,指针的类型只是给编译器看的。


其次,模版在实例化的过程中,不管谁包含了这个模版的头文件并以什么类型使用了这个模版,编译器将对一个类型只生成一份对应的实例。所以,如果我们的a.h里面实现了一个CMyClass的单件类,然后我们在a.cpp b.cpp中都包含了 a.h,因为模版实例化的特性,相对于Singleton<CMyClass>::m_psInstance 这个变量将只存在一份实例,不会在链接时出现多重定义的情况。


那么我们的 CDataMgr实例化后是什么情况呢?伪代码可能如下:

//
// 编译器自动加上的前向声明.
//
class CDataMgr;

//
// 用 CDataMgr 实例化的单件基类.
//
class Singleton<CDataMgr>

public:
	// ...
	
	static CDataMgr& GetInstance()
	
		// ...
		return *m_psInstance;
	
	
private:
	static CDataMgr*	m_psInstance;
;


CDataMgr* Singleton<CDataMgr>::m_psInstance = 0;


//
// 编译器处理后的类 CDataMgr.
//
class CDataMgr : public Singleton<CDataMgr>

public:
	// ...
	
	void SaveData();
;

这样一来,整个过程就非常容易理解了,这个模版使用起来非常方便。如果非常复杂的系统,还可以加上单件的管理,比如单件类初始化顺序管理、单件类释放顺序管理等等。





以上是关于C++工具箱——单件模版类的主要内容,如果未能解决你的问题,请参考以下文章

C++——函数模版与类模版

四单件模式

C++工具箱——定时器

单件模式

设计模式--单例模式C++实现

线程安全的单件模式(单例模式)