zoukankan      html  css  js  c++  java
  • c++ std:call_once 与 单例模式实现

    知识点

    c++ std:call_once 可以用于保证某个函数在多线程环境下只被调用一次。

    std::enable_if 泛型编程中模板最优匹配原则,template<bool Cond, class T = void> struct enable_if {}; //The type T is enabled as member type enable_if::type if Cond is true.
    std::decltype 表达式类型推导,该推导过程在编译期完成,并不会真正对表达式求值。
    constexpr 声明时带有constexpr关键字的变量是常量表达式,因而可以被用做编译期计算。
    如果带有constexpr的函数的参数被编译器检测到为编译期常量,那么这个函数就可以自动地在编译期运行。
     
    c++ 技巧,如何判断某个class 是否有某个成员函数 Shutdown
     
    template <typename T>                                   
    struct HasShutdown {                                           
    template <typename Class>                             
    static constexpr bool Test(decltype(&Class::Shutdown)*) { 
      return true;                                        
    }                                                     
    template <typename>                                   
    static constexpr bool Test(...) {                     
      return false;                                       
    }                                                     
                                                          
    static constexpr bool value = Test<T>(nullptr);       
    };                                                      
                                                          
    template <typename T>                                   
    constexpr bool HasShutdown<T>::value;
    
    template <typename T>
    typename std::enable_if<HasShutdown<T>::value>::type CallShutdown(T *instance) {
      instance->Shutdown();
    }
    
    template <typename T>
    typename std::enable_if<!HasShutdown<T>::value>::type CallShutdown(T *instance) {
      (void)instance;
    }
    
    class Singleton
    {
    public:
        static Singleton* Instance(bool create_if_needed = true) {
            static Singleton *instance = nullptr;
            if (!instance && create_if_needed) { 
                static std::once_flag flag;
                std::call_once(flag,
                    [&] { instance = new (std::nothrow) Singleton(); });
            }
            return instance;
        }
        static void CleanUp() {
            auto instance = Instance(false);
            if (instance != nullptr) {
                //delete instance;
                CallShutdown(instance); 
            }
        }     
    private:
        Singleton();
        ~Singleton();
    };
  • 相关阅读:
    线段树专辑—— pku 1436 Horizontally Visible Segments
    线段树专辑——pku 3667 Hotel
    线段树专辑——hdu 1540 Tunnel Warfare
    线段树专辑—— hdu 1828 Picture
    线段树专辑—— hdu 1542 Atlantis
    线段树专辑 —— pku 2482 Stars in Your Window
    线段树专辑 —— pku 3225 Help with Intervals
    线段树专辑—— hdu 1255 覆盖的面积
    线段树专辑—— hdu 3016 Man Down
    Ajax跨域访问
  • 原文地址:https://www.cnblogs.com/rayfloyd/p/14307182.html
Copyright © 2011-2022 走看看