单例模式很简单,也很常用,但是在各个具体语言中的实现方式又有很多值得考究的细节;
Java里有懒汉式(延迟实例化)、饿汉式(提前实例化),再加上线程安全,能做的很复杂;
C++里也有“局部静态变量”的妙用,也有一堆默认构造函数(默认构造函数、拷贝构造函数、重载赋值符号)需要私有化的麻烦;
每次要将一个类做成单例的时候,都要私有化一堆构造函数,再增加一个获取实例的静态方法,确实比较麻烦;
所以可以利用C++强大的模板编程(编译期多态),实现一个单例模板:
- #ifndef SINGLETON_H
- #define SINGLETON_H
- /**
- * tips: C++ Template Class
- * 需要将与模板类型T相关的实现全部放在头文件中
- * 这样编译器才能在编译期将所有的模板类型替换
- */
- template<typename T>
- class Singleton
- {
- private:
- Singleton() {}
- Singleton(const Singleton &);
- Singleton & operator = (const Singleton &);
- public:
- static T * getInstance()
- {
- //局部静态变量,延时初始化,并一直保有该实例
- //程序退出时,可以保证调用实例的析构方法释放资源
- static T instance;
- static T *pt = &instance;
- return pt;
- }
- };
- #endif // SINGLETON_H
这样,使用的时候只需要将具体的类塞进该模板即可:
- //singleton
- Singleton<MySingleton>::getInstance()->test();
Tips:不要忽略细节与其所以然!
细节1:
C++ Template Class 需要将与模板类型T相关的实现全部放在头文件中;
这是因为编译器需要在编译期将所有的模板类型替换成具体类型;
细节2:
注意局部静态变量的初始化时机与生命周期;
注意设计单例时,能够在程序退出时,释放单例所占用的资源——这里利用局部静态变量的析构方法来释放资源;