日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問(wèn) 生活随笔!

生活随笔

當(dāng)前位置: 首頁(yè) > 编程语言 > c/c++ >内容正文

c/c++

设计模式C++实现(8)——代理模式

發(fā)布時(shí)間:2025/3/20 c/c++ 33 豆豆
生活随笔 收集整理的這篇文章主要介紹了 设计模式C++实现(8)——代理模式 小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

? ? 軟件領(lǐng)域中的設(shè)計(jì)模式為開(kāi)發(fā)人員提供了一種使用專家設(shè)計(jì)經(jīng)驗(yàn)的有效途徑。設(shè)計(jì)模式中運(yùn)用了面向?qū)ο缶幊陶Z(yǔ)言的重要特性:封裝、繼承、多態(tài),真正領(lǐng)悟設(shè)計(jì)模式的精髓是可能一個(gè)漫長(zhǎng)的過(guò)程,需要大量實(shí)踐經(jīng)驗(yàn)的積累。最近看設(shè)計(jì)模式的書(shū),對(duì)于每個(gè)模式,用C++寫(xiě)了個(gè)小例子,加深一下理解。主要參考《大話設(shè)計(jì)模式》和《設(shè)計(jì)模式:可復(fù)用面向?qū)ο筌浖幕A(chǔ)》(DP)兩本書(shū)。本文介紹代理模式的實(shí)現(xiàn)。

??????? [DP]上的定義:為其他對(duì)象提供一種代理以控制對(duì)這個(gè)對(duì)象的訪問(wèn)。有四種常用的情況:(1)遠(yuǎn)程代理,(2)虛代理,(3)保護(hù)代理,(4)智能引用。本文主要介紹虛代理和智能引用兩種情況。

???????考慮一個(gè)可以在文檔中嵌入圖形對(duì)象的文檔編輯器。有些圖形對(duì)象的創(chuàng)建開(kāi)銷很大。但是打開(kāi)文檔必須很迅速,因此我們?cè)诖蜷_(kāi)文檔時(shí)應(yīng)避免一次性創(chuàng)建所有開(kāi)銷很大的對(duì)象。這里就可以運(yùn)用代理模式,在打開(kāi)文檔時(shí),并不打開(kāi)圖形對(duì)象,而是打開(kāi)圖形對(duì)象的代理以替代真實(shí)的圖形。待到真正需要打開(kāi)圖形時(shí),仍由代理負(fù)責(zé)打開(kāi)。這是[DP]一書(shū)上的給的例子。下面給出代理模式的UML圖。

?????? 簡(jiǎn)單實(shí)現(xiàn)如下:

[cpp]?view plaincopy print?
  • class?Image??
  • {??
  • public:??
  • ????Image(string?name):?m_imageName(name)?{}??
  • ????virtual?~Image()?{}??
  • ????virtual?void?Show()?{}??
  • protected:??
  • ????string?m_imageName;??
  • };??
  • class?BigImage:?public?Image??
  • {??
  • public:??
  • ????BigImage(string?name):Image(name)?{}??
  • ????~BigImage()?{}??
  • ????void?Show()?{?cout<<"Show?big?image?:?"<<m_imageName<<endl;?}??
  • };??
  • class?BigImageProxy:?public?Image??
  • {??
  • private:??
  • ????BigImage?*m_bigImage;??
  • public:??
  • ????BigImageProxy(string?name):Image(name),m_bigImage(0)?{}??
  • ????~BigImageProxy()?{?delete?m_bigImage;?}??
  • ????void?Show()???
  • ????{??
  • ????????if(m_bigImage?==?NULL)??
  • ????????????m_bigImage?=?new?BigImage(m_imageName);??
  • ????????m_bigImage->Show();??
  • ????}??
  • };??
  • ?????????客戶調(diào)用:

    [cpp]?view plaincopy print?
  • int?main()??
  • {??
  • ????Image?*image?=?new?BigImageProxy("proxy.jpg");?//代理??
  • ????image->Show();?//需要時(shí)由代理負(fù)責(zé)打開(kāi)??
  • ????delete?image;??
  • ????return?0;??
  • }??
  • ???????? 在這個(gè)例子屬于虛代理的情況,下面給兩個(gè)智能引用的例子。一個(gè)是C++中的auto_ptr,另一個(gè)是smart_ptr。自己實(shí)現(xiàn)了一下。先給出auto_ptr的代碼實(shí)現(xiàn):

    [cpp]?view plaincopy print?
  • template<class?T>????
  • class?auto_ptr?{????
  • public:????
  • ????explicit?auto_ptr(T?*p?=?0):?pointee(p)?{}????
  • ????auto_ptr(auto_ptr<T>&?rhs):?pointee(rhs.release())?{}????
  • ????~auto_ptr()?{?delete?pointee;?}????
  • ????auto_ptr<T>&?operator=(auto_ptr<T>&?rhs)????
  • ????{????
  • ????????if?(this?!=?&rhs)?reset(rhs.release());????
  • ????????return?*this;????
  • ????}????
  • ????T&?operator*()?const?{?return?*pointee;?}????
  • ????T*?operator->()?const?{?return?pointee;?}????
  • ????T*?get()?const?{?return?pointee;?}????
  • ????T*?release()????
  • ????{????
  • ????????T?*oldPointee?=?pointee;????
  • ????????pointee?=?0;????
  • ????????return?oldPointee;????
  • ????}????
  • ????void?reset(T?*p?=?0)????
  • ????{????
  • ????????if?(pointee?!=?p)?{????
  • ???????????????delete?pointee;????
  • ???????????????pointee?=?p;????
  • ????????????}????
  • ????????}????
  • private:????
  • ????T?*pointee;????
  • };????
  • ????????閱讀上面的代碼,我們可以發(fā)現(xiàn) auto_ptr 類就是一個(gè)代理,客戶只需操作auto_prt的對(duì)象,而不需要與被代理的指針pointee打交道。auto_ptr?的好處在于為動(dòng)態(tài)分配的對(duì)象提供異常安全。因?yàn)樗靡粋€(gè)對(duì)象存儲(chǔ)需要被自動(dòng)釋放的資源,然后依靠對(duì)象的析構(gòu)函數(shù)來(lái)釋放資源。這樣客戶就不需要關(guān)注資源的釋放,由auto_ptr 對(duì)象自動(dòng)完成。實(shí)現(xiàn)中的一個(gè)關(guān)鍵就是重載了解引用操作符和箭頭操作符,從而使得auto_ptr的使用與真實(shí)指針類似。

    ???????我們知道C++中沒(méi)有垃圾回收機(jī)制,可以通過(guò)智能指針來(lái)彌補(bǔ),下面給出智能指針的一種實(shí)現(xiàn),采用了引用計(jì)數(shù)的策略。

    [cpp]?view plaincopy print?
  • template?<typename?T>??
  • class?smart_ptr??
  • {??
  • public:??
  • ????smart_ptr(T?*p?=?0):?pointee(p),?count(new?size_t(1))?{?}??//初始的計(jì)數(shù)值為1??
  • ????smart_ptr(const?smart_ptr?&rhs):?pointee(rhs.pointee),?count(rhs.count)?{?++*count;?}?//拷貝構(gòu)造函數(shù),計(jì)數(shù)加1??
  • ????~smart_ptr()?{?decr_count();?}??????????????//析構(gòu),計(jì)數(shù)減1,減到0時(shí)進(jìn)行垃圾回收,即釋放空間??
  • ????smart_ptr&?operator=?(const?smart_ptr&?rhs)?//重載賦值操作符??
  • ????{??
  • ????????//給自身賦值也對(duì),因?yàn)槿绻陨碣x值,計(jì)數(shù)器先減1,再加1,并未發(fā)生改變??
  • ????????++*count;??
  • ????????decr_count();??
  • ????????pointee?=?rhs.pointee;??
  • ????????count?=?rhs.count;??
  • ????????return?*this;??
  • ????}????
  • ????//重載箭頭操作符和解引用操作符,未提供指針的檢查??
  • ????T?*operator->()?{?return?pointee;?}??
  • ????const?T?*operator->()?const?{?return?pointee;?}??
  • ????T?&operator*()?{?return?*pointee;?}??
  • ????const?T?&operator*()?const?{?return?*pointee;?}??
  • ????size_t?get_refcount()?{?return?*count;?}?//獲得引用計(jì)數(shù)器值??
  • private:???
  • ????T?*pointee;???????//實(shí)際指針,被代理????
  • ????size_t?*count;????//引用計(jì)數(shù)器??
  • ????void?decr_count()?//計(jì)數(shù)器減1??
  • ????{??
  • ????????if(--*count?==?0)???
  • ????????{??
  • ????????????delete?pointee;??
  • ????????????delete?count;??
  • ????????}??
  • ????}??
  • };??
  • ? ? ? ?

    《新程序員》:云原生和全面數(shù)字化實(shí)踐50位技術(shù)專家共同創(chuàng)作,文字、視頻、音頻交互閱讀

    總結(jié)

    以上是生活随笔為你收集整理的设计模式C++实现(8)——代理模式的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。

    如果覺(jué)得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。