单例模式

设计模式--单例模式:
创建一个安全并且高效的Sington很重要。
(1)单例类保证全局只有一个唯一实例对象;
(2)单例类提供获取这个唯一实例的接口。
下面为四种创建单例类的方法:

 //单例模式
////////不考虑线程安全的单例类//////////
class Singleton
{
public:

           //获取唯一对象实例的接口函数
           static Singleton * GetIntance()
          {
                    if (_sIntance == NULL )
                   {
                              if (_sIntance == NULL )
                             {
                                      _sIntance = new Singleton ();
                             }
                   }
                    return _sIntance;
          }

           //删除实例对象
           static void DelIntance()
          {
                    if (_sIntance)
                   {
                              delete _sIntance;
                             _sIntance = NULL;
                   }
          }

           void Print()
          {
                   cout << _data << endl;

          }

private:
           //构造函数定义为私有,限制只能在类内创建对象
          Singleton()
                   :_data(0)
          {}

           //防拷贝
          Singleton( const Singleton &);
           Singleton& operator=(const Singleton&);
private:
           static Singleton * _sIntance;//指向实例的指针定义为静态私有,定义静态函数获取实例对象
           int _data;//单例类里的数据
};

Singleton* Singleton ::_sIntance = NULL; //静态成员只能在类外初始化

void TestSingleton()
{
           Singleton::GetIntance()->Print();
           Singleton::DelIntance();
}
 ////////////线程安全的单例模式(懒汉模式)////////////
class Singleton
{
public:
           //获取唯一对象实例的接口函数
           static Singleton * GetIntance()
          {
                    //使用双重检查,提高效率,避免高并发场景下每次获得实例对象都进行加锁,浪费资源
                    if (_sIntance == NULL )
                   {
                             std:: lock_guard<std::mutex > lck(_mtx);
                              if (_sIntance == NULL )
                             {
                                       Singleton* tmp = new Singleton();
                                      MemoryBarrier(); //内存栅栏,防止编译器重排栅栏后的赋值到栅栏之前
                                      _sIntance = tmp;
                             }
                   }
                    return _sIntance;
          }

           //删除实例对象
           static void DelIntance()
          {
                   std:: lock_guard<std::mutex > lck(_mtx);
                    if (_sIntance)
                   {
                              delete _sIntance;
                             _sIntance = NULL;
                   }
          }

           void Print()
          {
                   cout << _data << endl;

          }


private:
           //构造函数定义为私有,限制只能在类内创建对象
          Singleton()
                   :_data(0)
          {}
          
           //防拷贝
          Singleton( const Singleton &);
           Singleton& operator=(const Singleton&);

private:
           static mutex _mtx;//保证线程安全的互斥锁
           static Singleton * _sIntance;//指向实例的指针定义为静态私有,定义静态函数获取实例对象
           int _data;//单例类里的数据
};

Singleton* Singleton ::_sIntance = NULL; //静态成员只能在类外初始化
mutex Singleton::_mtx;

void TestSingleton()
{
           Singleton::GetIntance()->Print();
           Singleton::DelIntance();
}
  /////////////饿汉模式(简洁,不加锁)/////////////////////////
class Singleton
{
public:

           //获取唯一对象实例的接口函数
           static Singleton * GetIntance()
          {
                    static Singleton sIntance;
                    return &sIntance;
          }

           void Print()
          {
                   cout << _data << endl;
          }

private:
           //构造函数定义为私有,限制只能在类内创建对象
          Singleton()
                   :_data(0)
          {}

           //防拷贝
          Singleton( const Singleton &);
           Singleton& operator=(const Singleton&);
private:
           int _data;//单例类里的数据
};

void TestSingleton()
{
           Singleton::GetIntance()->Print();
}





////////// /////饿汉模式2////////////////////
class Singleton
{
public:

           //获取唯一对象实例的接口函数
           static Singleton *GetIntance()
          {
                    assert(_sIntance);
                    return _sIntance;
          }

           //删除实例对象
           static void DelIntance()
          {
                    if (_sIntance)
                   {
                              delete _sIntance;
                             _sIntance = NULL;
                   }
          }

           void Print()
          {
                   cout << _data << endl;
          }

private:
           //构造函数定义为私有,限制只能在类内创建对象
          Singleton()
                   :_data(0)
          {}

           //防拷贝
          Singleton( const Singleton &);
           Singleton& operator=(const Singleton&);
private:
           static Singleton * _sIntance;//指向实例的指针定义为静态私有,定义静态函数获取实例对象
           int _data;//单例类里的数据
};

Singleton* Singleton ::_sIntance = new Singleton; //静态成员只能在类外初始化

void TestSingleton()
{
           Singleton::GetIntance()->Print();
           Singleton::DelIntance();
}
 ///////////////使用RAII GC自动回收实例对象的方式///////////
class Singleton
{
public:

           //获取唯一对象实例的接口函数
           static Singleton * GetIntance()
          {
                    assert(_sIntance);
                    return _sIntance;
          }

           //删除实例对象
           static void DelIntance()
          {
                    if (_sIntance)
                   {
                              delete _sIntance;
                             _sIntance = NULL;
                   }
          }

           void Print()
          {
                   cout << _data << endl;

          }

           class GC
          {
           public:
                   ~GC()
                   {
                             cout << "DelIntance" << endl;
                             DelIntance();
                   }
          };

private:
           //构造函数定义为私有,限制只能在类内创建对象
          Singleton()
                   :_data(0)
          {}

           //防拷贝
          Singleton( const Singleton &);
           Singleton& operator=(const Singleton&);
private:
           static Singleton * _sIntance;//指向实例的指针定义为静态私有,定义静态函数获取实例对象
           int _data;//单例类里的数据
};

Singleton* Singleton ::_sIntance = new Singleton; //静态成员只能在类外初始化

//使用RAII,定义全局的GC对象释放对象实例
Singleton::GC gc;

void TestSingleton()
{
           Singleton::GetIntance()->Print();
}

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章