今天在学习平台学习了一份比较有意思并且非常厉害的代码,就是设计模式的单例。设计模式这种类型的书以及网上的资料也看过不少,但是都是比较普通的写法,懒汉模式、饿汉模式等等。
今天这份单例使用了以下知识点,模板、可变参模板、二级指针、以及完美转发。
1、单例
// 单例 工业级 template<typename T> class Global final { public: static T* Get() { return *GetPPtr(); } template<typename... Args> static void New(Args&&... args) { assert(Get() == nullptr); *GetPPtr() = new T(std::forward<Args>(args)...); } static void Delete() { if (Get() != nullptr) { delete Get(); *GetPPtr() = nullptr; std::cout << "删除对象" << std::endl; } } private: static T** GetPPtr() { static T* ptr = nullptr; return &ptr; } };
2、测试类
class MySingleClass { private: std::string name; public: MySingleClass(const std::string& n) :name(n) { std::cout << "左值构造函数" << std::endl; } MySingleClass(const std::string&& n) :name(n) { std::cout << "右值构造函数" << std::endl; } void PrintName() { std::cout << name << std::endl; } ~MySingleClass() { std::cout << "调用析构函数" << std::endl; } };
3、测试例子
int main() { // new出来一个对象的单例,存在Move语义,则执行move语义 // 临时对象,并未显示创建 Global<MySingleClass>::New("123"); // 调用对象的成员函数 Global<MySingleClass>::Get()->PrintName(); // 删除对象 // 不会调用123的析构函数,会在函数结束之后,调用123的析构函数 Global<std::string>::Delete(); // 显示创建一份对象 MySingleClass myclass("1234"); Global<MySingleClass>::New(myclass); Global<MySingleClass>::Get()->PrintName(); // 会删除myclass对象,并调用其析构函数 Global<MySingleClass>::Delete(); }
其例子的输出如下:
右值构造函数
123
右值构造函数
1234
调用析构函数
删除对象
调用析构函数
这个单例参考的是oneFlow的代码以及某学习平台某位仙女的视频