C++ 單例類别範本(詳解)
單例類
描述
指在整個系統生命期中,一個類最多隻能有一個例項(instance)存在,使得該例項的唯一性(例項是指一個物件指標) , 比如:統計線上人數
在單例類裡,又分為了懶漢式和餓漢式,它們的區別在於建立例項的時間不同:
懶漢式 : 指程式碼執行後,例項並不存在,只有當需要時,才去建立例項(適用於單執行緒)
餓漢式 : 指程式碼一執行,例項已經存在,當時需要時,直接去呼叫即可(適用於多執行緒)
用法
將建構函式的訪問屬性設定為private,
提供一個GetInstance()靜態成員函式,只能供使用者訪問唯一一個例項.
定義一個靜態成員指標,用來供使用者獲取
過載 (=)賦值操作符以及拷貝建構函式,並設為private, 避免物件間拷貝,複製.
初探單例類-懶漢式:
複製程式碼
#include
using namespace std;
class CSingleton
{
private:
static CSingleton* m_pInstance;
CSingleton() //建構函式為private
{
}
CSingleton& operator = (const CSingleton& t);
CSingleton(const CSingleton &);
public:
static CSingleton* getInstance()
{
if(m_pInstance==NULL)
m_pInstance= new CSingleton();
return m_pInstance;
}
void print()
{
cout<<this<<endl;
}
};
CSingleton* CSingleton::m_pInstance = NULL;
int main()
{
CSingleton *p1=CSingleton::getInstance();
CSingleton *p2=CSingleton::getInstance();
CSingleton *p3=CSingleton::getInstance();
p1->print();
p2->print();
p3->print();
return 0;
}
複製程式碼
執行列印:
0x6e2d18
0x6e2d18
0x6e2d18
從列印結果可以看出,該指標物件指向的都是同一個地址,實現了一個類最多隻能有一個例項(instance)存在.
注意:由於例項(instance),在系統生命期中,都是存在的,所以只要系統還在執行,就不需要delete
上面的懶漢式如果在多執行緒情況下 ,多個Csingleton指標物件同時呼叫getInstance()成員函式時,由於m_pInstance = NULL,就會建立多個例項出來.(除非使用mutex來新增互斥)
所以,在多執行緒情況下,需要使用餓漢實現
程式碼如下:
複製程式碼
class CSingleton
{
private:
static CSingleton* m_pInstance;
CSingleton() //建構函式為private
{
}
CSingleton& operator = (const CSingleton& t);
CSingleton(const CSingleton &);
public:
static CSingleton* getInstance()
{
return m_pInstance;
}
};
CSingleton* CSingleton::m_pInstance = new CSingleton;
複製程式碼
也可以直接粗暴的用static變數:
複製程式碼
class CSingleton
{
private:
CSingleton() //建構函式為private
{
}
CSingleton& operator = (const CSingleton& t);
CSingleton(const CSingleton &);
public:
static CSingleton* getInstance()
{
static CSingleton Instance;
return &Instance;
}
};
複製程式碼
注意:
類函式中如果使用static靜態區域性變數,那麼該變數是不安全的,因為static變數是一直存在的,所有物件都會共享這個變數.
單例類别範本
我們現在講解的僅僅是個框架,裡面什麼都沒有,不能滿足需求啊,所以還要寫為單例類别範本標頭檔案,當需要單例類時,直接宣告單例類别範本標頭檔案即可
寫CSingleton.h
複製程式碼
#ifndef SINGLETON_H
#define SINGLETON_H
template
class CSingleton
{
private:
static T* m_pInstance;
CSingleton() //建構函式為private
{
}
public:
static T* getInstance()
{
return m_pInstance;
}
};
template
T* CSingleton :: m_pInstance = new T;
#endif
複製程式碼
當我們需要這個單例類别範本時,只需要在自己類裡通過friend新增為友元即可,
接下來試驗單例類别範本
寫main.cpp
複製程式碼
#include
#include
#include “CSingleton.h”
using namespace std;
class Test
{
friend class CSingleton ; //宣告Test的友元為單例類别範本
private:
string mstr;
Test(): mstr("abc")
{
}
Test& operator = (const Test& t);
Test(const Test&);
public:
void Setmstr(string t)
{
mstr=t;
}
void print()
{
cout<<"mstr = "<<mstr<<endl;
cout<<"this = "<<this<<endl;
}
};
int main()
{
Test *pt1 = CSingleton::getInstance();
Test *pt2 = CSingleton::getInstance();
pt1->print();
pt2->print();
pt1->Setmstr("ABCDEFG");
pt2->print();
return 0;
}
複製程式碼
執行列印:
複製程式碼
mstr = abc
this = 0x2d2e30
mstr = abc
this = 0x2d2e30
mstr = ABCDEFG
this = 0x2d2e30
複製程式碼
相關文章
- 類别範本 單例模板單例
- 隱藏在 SDK 中的單例類别範本單例
- C++ 類别範本的寫法C++
- 類别範本
- c++函式模板和類别範本C++函式
- 【C++】 59_類别範本深度剖析C++
- 【C++】 61_智慧指標類别範本C++指標
- 陣列類别範本陣列
- C++知識點57——類别範本(2、類别範本的區域性特化與預設模板實參)C++
- 類别範本與繼承繼承
- 類别範本與友元
- 類别範本的常見用法
- pua 八股類别範本
- C++ Templates (2.2 使用Stack類别範本 Use of Class Template Stack )C++
- C++ Templates (2.1 類别範本Stack的實現 Implementation of Class Template Stack)C++
- C++學習筆記 第59課類别範本深度刨析C++筆記
- 資料結構初階--單連結串列(講解+類别範本實現)資料結構
- C++ Templates (2.3 類别範本的區域性使用 Partial Usage of Class Templates)C++
- 【C++ 泛型程式設計01:模板】函式模板與類别範本C++泛型程式設計函式
- 類别範本與函式模板的區別函式
- 類别範本中成員函式建立時機函式
- c++11-17 模板核心知識(二)—— 類别範本C++
- 類别範本的簡單應用(用於儲存不同型別資料的類容器)型別
- 資料結構初階--棧和佇列(講解+類别範本實現)資料結構佇列
- 封裝不同類别範本的隨機數生成器封裝隨機
- 【演算法學習】數學專題 有理數類别範本演算法
- 類别範本及其成員函式的定義及注意事項函式
- 資料結構初階--雙向迴圈連結串列(講解+類别範本實現)資料結構
- 類别範本物件做函式引數物件函式
- VS2017 設定 類别範本引數推導(CTAD, Class Template Argument Deduction)
- java-單例詳解Java單例
- python單例的使用詳解Python單例
- C++類和物件是什麼?C++類和物件詳解C++物件
- c#中單例模式詳解C#單例模式
- EventBus詳解及簡單例項單例
- 關於C++中物件與類的詳解及其作用詳解C++物件
- 設計模式之單例模式詳解設計模式單例
- java和C++之單例類雙重檢查加鎖JavaC++單例