28.C++- 單例類模板(詳解)

来源:https://www.cnblogs.com/lifexy/archive/2018/04/12/8810877.html
-Advertisement-
Play Games

單例類 描述 指在整個系統生命期中,一個類最多只能有一個實例(instance)存在,使得該實例的唯一性(實例是指一個對象指針) , 比如:統計線上人數 在單例類里,又分為了懶漢式和餓漢式,它們的區別在於創建實例的時間不同: 懶漢式 : 指代碼運行後,實例並不存在,只有當需要時,才去創建實例(適用於 ...


單例類

描述

指在整個系統生命期中,一個類最多只能有一個實例(instance)存在,使得該實例的唯一性(實例是指一個對象指針)  , 比如:統計線上人數

 

在單例類里,又分為了懶漢式餓漢式,它們的區別在於創建實例的時間不同:

  • 懶漢式 : 指代碼運行後,實例並不存在,只有當需要時,才去創建實例(適用於單線程)
  • 餓漢式 : 指代碼一運行,實例已經存在,當時需要時,直接去調用即可(適用於多線程)

 

用法

  • 將構造函數的訪問屬性設置為private,
  • 提供一個GetInstance()靜態成員函數,只能供用戶訪問唯一一個實例.
  • 定義一個靜態成員指針,用來供用戶獲取
  • 重載 (=)賦值操作符以及拷貝構造函數,並設為private, 避免對象間拷貝,複製.

 

初探單例類-懶漢式:

#include <iostream>
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,就會創建多個實例出來.

 

所以,在多線程情況下,需要使用餓漢實現

代碼如下:

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;

 

 

單例類模板

我們現在講解的僅僅是個框架,裡面什麼都沒有,不能滿足需求啊,所以還要寫為單例類模板頭文件,當需要單例類時,直接聲明單例類模板頭文件即可

寫CSingleton.h

#ifndef _SINGLETON_H_
#define _SINGLETON_H_

template <typename T>
class CSingleton
{
private:
        static T* m_pInstance;
CSingleton()
//構造函數為private {
     }
public: static T* getInstance() { return m_pInstance; } }; template <typename T> T* CSingleton<T> :: m_pInstance = new T; #endif

當我們需要這個單例類模板時,只需要在自己類里通過friend添加為友元即可,

 

接下來試驗單例類模板

寫main.cpp

#include <iostream>
#include <string>
#include "CSingleton.h"

using namespace std;

class Test
{
       friend class CSingleton<Test> ;  //聲明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<Test>::getInstance();
        Test *pt2 = CSingleton<Test>::getInstance();   

        pt1->print();
        pt2->print();

        pt1->Setmstr("ABCDEFG");
        pt2->print();

        return 0;
}

運行列印:

mstr = abc
this = 0x2d2e30

mstr = abc
this = 0x2d2e30

mstr = ABCDEFG
this = 0x2d2e30

 

 

 


您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 一、hibernate中的核心配置文件:hibernate.rfg.xml 對於hibernate的核心配置文件有兩種:1.hibernate.rfg.xml,2.hibernate.properties。開發中我們最常用的是hibernate.rfg.xml的配置文件,因為它的配置能力強,易於修改 ...
  • 什麼是過濾器 過濾器就是 Servlet 的高級特性之一, 就是一個具有 攔截/過濾 功能的一個東西,在生活中過濾器可以是香煙濾嘴,濾紙,凈水器,空氣凈化器等,在 Web 中僅僅是一個 實現了 Filter 介面的 Java 類 而已。 特點:雙向,攔截請求,攔截響應 作用: 過濾器可以對 所有的請 ...
  • 水仙花數業內的大家可能聽說過,但是對於初學者來講,對於水仙花數還是比較陌生的。 首先要知道的是水仙花數的計算公式:153=1**3+5**3+3**3: 如何去判定這個數是否為水仙花數,最好的辦法就是用for內嵌迴圈了,因為涉及到了公式所以很多數學邏輯不是很好的兄臺,就尷尬了,其實有一個比較簡單的數 ...
  • 閱讀目錄 屬性初始化和構造器調用 初始化的順序 靜態塊和非靜態塊 初始化的方式 數組初始化 閱讀目錄 閱讀目錄 屬性初始化和構造器調用 初始化的順序 靜態塊和非靜態塊 初始化的方式 數組初始化 屬性初始化和構造器調用 初始化的順序 靜態塊和非靜態塊 初始化的方式 數組初始化 一、屬性初始化和構造器調 ...
  • 重點不是說PageRank是什麼,而是怎麼用代碼實現 什麼是PageRank? PageRank,網頁排名,又稱網頁級別、Google左側排名或佩奇排名,是一種由[1] 根據網頁之間相互的超鏈接計算的技術,而作為網頁排名的要素之一,以Google公司創辦人拉里·佩奇(Larry Page)之姓來命名 ...
  • 1. 遇到的問題 已知一個題庫,希望實現當前頁切換上一題,下一題的需求。 查看得知,資料庫中用於查詢的欄位(主鍵)是不連續的。如上圖所示:stxh為主鍵number類型。 2. 實現方式lead over 2.1 實現代碼 2.2 lead方法說明 lead(value_expr [,offset] ...
  • 登陸介面並實現猜數字游戲 輸入用戶名密碼 認證成功後顯示歡迎信息 進行猜數字游戲,可猜三次 輸錯三次後鎖定 輸入用戶名密碼 認證成功後顯示歡迎信息 進行猜數字游戲,可猜三次 輸錯三次後鎖定 1、Adduser.py 1 # The author is tou 2 import pickle 3 #初 ...
  • 一、概述 作為一個在八本學校在校生,沒有實驗室,也沒有項目可做。一直想做一個個人博客,一年前學完javaweb之後做了一個簡單的博客,ui慘不忍睹就算了,還有各種bug。醞釀了很久,寒假用了將近一個月時間做出了現在這個網站,本項目致力於打造一個高併發,高可用,高性能的網站,由於本人實力有限,目前還是 ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...