第13章計模式DesignPattern_第1頁
第13章計模式DesignPattern_第2頁
第13章計模式DesignPattern_第3頁
第13章計模式DesignPattern_第4頁
第13章計模式DesignPattern_第5頁
已閱讀5頁,還剩33頁未讀, 繼續(xù)免費閱讀

下載本文檔

版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請進行舉報或認領(lǐng)

文檔簡介

1、第13章 設(shè)計模式(design pattern )132 可重用的面向?qū)ο笤O(shè)計模式可重用的面向?qū)ο笤O(shè)計模式13.2.1 設(shè)計模式概述設(shè)計模式概述1. 面向?qū)ο笤O(shè)計的任務(wù):面向?qū)ο笤O(shè)計的任務(wù):應(yīng)用系統(tǒng)設(shè)計應(yīng)用系統(tǒng)設(shè)計工具庫設(shè)計工具庫設(shè)計框架設(shè)計框架設(shè)計其中,框架是已形成源代碼的可重用軟件體系結(jié)構(gòu)。它體現(xiàn)了應(yīng)用程序的模塊組成關(guān)系。框架及框架中的各個模塊是形形色色各具特色的。設(shè)計模式(design pattern)描述了軟件開發(fā)過程中若干重復(fù)出現(xiàn)的問題的解決方案,這些方案不是由過程、算法等底層程序構(gòu)造實體實現(xiàn),而是由軟件系統(tǒng)中類與類之間或不同類的對象之間的共生關(guān)系組成。設(shè)計模式可以幫助軟件設(shè)計人員

2、學(xué)習(xí)、重用前人的經(jīng)驗和成果。設(shè)計模式的分類整理最早見于erich gamma在德國慕尼黑大學(xué)的博士論文。1995年,erich gamma,richard helm,ralph johnson,john vlissides合著的design patterns:elements of reusable object_oriented software系統(tǒng)地整理和描述了23個精選的設(shè)計模式(gof模式),為設(shè)計模式的學(xué)習(xí)、研究和推廣提供了良好的范例。classnamefunction1()function2()datamenber1datamenber2類的表示:子類關(guān)系:baseclasssub

3、class2設(shè)計模式的描述符號設(shè)計模式的描述符號(1)類和對象的表示 對象及對象鏈接:aobjectanotherobject(2)連接的表示)連接的表示 例如:由類a創(chuàng)建類b的對象 classaclassb對象創(chuàng)建關(guān)系:對象創(chuàng)建關(guān)系:示例代碼:classa:create() return new classb;實例引用關(guān)系實例引用關(guān)系:classaclassbrefrencename(引用名可選)window:area()return arectarea();windowarea()rectanglearea()widthheightrectangle:area() return width

4、* height; 引用關(guān)系涉及到的兩個類的實例之間可以形成一種代理關(guān)系,接受請求的對象將操作委托給它的代理者:arect對象聚合關(guān)系:對象聚合關(guān)系:objectsclassaclassb如:下圖表示類a中聚合了多個類b的對象。聚合關(guān)系可以用對象成員實現(xiàn),但更經(jīng)常的是將聚合的成員定義為對象成員指針或引用。由于引用關(guān)系也是以對象成員指針或引用來實現(xiàn)的,注意從設(shè)計意圖上區(qū)分對象聚合關(guān)系和引用關(guān)系對理解設(shè)計模式是至關(guān)重要的。聚合是對象的包容關(guān)系,容器和容器中的對象具有相同的生命期。引用關(guān)系又稱相識關(guān)系,是一種較松散的耦合關(guān)系。具有引用關(guān)系的對象,僅僅是知道被引用者的存在,并不為對方負責(zé), 1抽象工廠

5、(抽象工廠(abstract factory)模式)模式抽象工廠定義一個抽象基類,為創(chuàng)建組合對象提供接口。在面向?qū)ο笙到y(tǒng)中,單個對象的創(chuàng)建由構(gòu)造函數(shù)負責(zé)。一個組合對象的動態(tài)創(chuàng)建可由一個創(chuàng)建函數(shù)創(chuàng)建函數(shù)一次性完成,以保證被創(chuàng)建的組合對象的完備性。抽象工廠定義的接口稱為創(chuàng)建函數(shù)或初始化函數(shù)。抽象工廠的不同實現(xiàn)類(可稱為實現(xiàn)工廠)的對象可以按不同的風(fēng)格去實現(xiàn)組合對象的具體創(chuàng)建,可以在保證組合對象被完備創(chuàng)建的前提下,簡化組合對象的版本替換、升級換代過程。工廠方法(工廠方法(factory method)是一些動態(tài)創(chuàng)建對象的方法。是在抽象工廠中聲明的一組虛函數(shù),它們負責(zé)組合對象中成員對象的創(chuàng)建,其實現(xiàn)代

6、碼在實現(xiàn)工廠中定義。 抽象工廠模式通常與工廠方法配合使用抽象工廠模式通常與工廠方法配合使用product1part11part12product2part21part22productfactoryproductcreate()factorymethod1()factorymethod2()concreatbfactorymethod1()factorymethod2()concreatafactorymethod1()factorymethod2()圖13.1 抽象工廠和工廠方法模式結(jié)構(gòu)舉例1創(chuàng)建函數(shù):創(chuàng)建函數(shù):一個抽象的產(chǎn)品工廠類productfactory定義了由 兩 個 零 件 組 成

7、 的 組 件 產(chǎn) 品 的 創(chuàng) 建 函 數(shù)product* productcreate (); 以及創(chuàng)建零件的工廠方法。抽象的產(chǎn)品工廠的實現(xiàn)工廠concreteproduct重定義了創(chuàng)建零件對象的工廠方法。創(chuàng)建函數(shù)product* productcreate ()調(diào)用工廠方法,一次性創(chuàng)建產(chǎn)品。返回產(chǎn)品指針。2產(chǎn)品類與零件類產(chǎn)品類與零件類產(chǎn)品類product與零件類part可以是分別定義的類,產(chǎn)品類以零件類為自己的對象成員。productcreate ()創(chuàng)建一個由2個part1和1個part2組合而成的product組合對象。如果將product定義為抽象基類,且part1和part2定義為它的

8、實現(xiàn)類,則可以得到更加復(fù)雜的product組合關(guān)系。class productfactory /抽象工廠定義public: product* productcreate ();virtual part1*factorymethod1();virtual part2*factorymethod2();/;class concretea: public productfactory /實現(xiàn)工廠定義public: virtual part1*factorymethod1() return new part1; ;virtual part2*factorymethod2() return new pa

9、rt2; ;/;product* productfactory: productcreate () product* ptr;part1* p11= factorymethod1();part1* p12= factorymethod1();part1* p21= factorymethod2();ptr=p11;return ptr;class product;class part1;class part2;3用工廠對象參數(shù)化參數(shù)化組合對象創(chuàng)建過程:工廠對象即實現(xiàn)工廠的實例對象。修改生產(chǎn)函數(shù)productcreate()如下:product* productcreate ( productf

10、actory* );/創(chuàng)建函數(shù)以抽象工廠的指針為形參。 若再定義一個抽象工廠的實現(xiàn)類:class concreteb: public productfactory然后聲明:concretea* factorya; concretetb* factoryb;則調(diào)用:productcreate (factorya);productcreate (factorya );將生產(chǎn)a、b兩個不同系列的產(chǎn)品。很容易實現(xiàn)產(chǎn)品系列的更新?lián)Q代。如:product和part分別代表電腦主機和配件,產(chǎn)品更新?lián)Q代只要定義新的抽象工廠的實現(xiàn)類,并用它來參數(shù)化生產(chǎn)函數(shù)即可,不必對系統(tǒng)的其它部分作任何改動。class app

11、licationstatic application * instance;application ( );public:static int count;application ( );static application* init();application *application:instance=null;int application:count=0;application *application:init() if (count=0) count=count+1; instance = new application; coutsingle instance has crea

12、ted, ok!endl; return instance; else coutcant create more than one instance!endl; return null; application:application()count=count-1;coutthe single instance has released! getpicture ()test-add(new rectangle); agraphic = arectangle;if (test = agraphic- getpicture ()test-add(new rectangle); /此次add ()操

13、作實際并不執(zhí)行 為了識別一個組件是基元還是組合,可按以下示例代碼,定義一 個 查 詢 函 數(shù)getpicture(),對其返回的組合安全地執(zhí)行add()和remove()操作:3共享對象(共享對象(flyweight)模式)模式:細粒度對象通常因為數(shù)量太大而難以用對象進行建模。共享對象模式提供解決這個難題的有效手段。例如:在文檔編輯器程序中,文檔對象可能是一個遞歸組合模式對象。若將文檔中的字符作為文檔組合對象樹的葉結(jié)點,可以將字符與文檔中的圖形、表格等嵌入部分的繪制和格式化作統(tǒng)一處理,并且在程序擴展,支持新字符集時不影響其它部分。但是成千上萬的字符對象將耗費大量內(nèi)存,并產(chǎn)生難以接受的運行開銷。

14、共享對象模式解決了這一問題,使大量細粒度對象的使用無須付出這些過于昂貴的代價。一個共享對象(flyweight)可以在多個上下文(context)對象中使用。在每個具體的上下文對象中,flyweight作為一個獨立的對象出現(xiàn),在這一點上與非共享對象沒有區(qū)別。flyweight的數(shù)據(jù)成員被看作它的“內(nèi)部狀態(tài)”,是只讀的。flyweight的上下文對象為flyweight提供上下文信息,它們被看作flyweight的“外部狀態(tài)”。用戶對象負責(zé)在必要的時候?qū)⑼獠繝顟B(tài)傳遞給flyweight。以文檔編輯器應(yīng)用為例,它為字母表中每一個字母創(chuàng)建一個共享對象(flyweight)。每個flyweight雖然

15、只存儲一個字母代碼,但它在文檔中的位置和排版風(fēng)格可以由排版算法或格式化命令決定。邏輯上,文檔中的字符每次出現(xiàn)都會有一個對象與之對應(yīng)。物理上,同一字符共享一個flyweight對象,即同一字符每次出現(xiàn)都指向同一實例,該實例位于對象的共享池中。 flyweight 對象池對象池abcdeihgflkjmnopqrvutsyxwzarowacolumnarowarowamerica4代理(代理(proxy)模式)模式代理模式的原型可以參考文件緩沖區(qū)與磁盤文件的關(guān)系。正如只有在需要訪問某個磁盤文件時才為它建立緩沖區(qū)的道理一樣,在面向?qū)ο笙到y(tǒng)中只有在確實需要某個對象時才對它進行創(chuàng)建和初始化。例如,當(dāng)需要

16、打開一個多媒體文檔時,如果一次性打開其中包含的所有對象,往往造成不必要的巨大開銷,因為這些對象在文檔中并不是同時可見的,沒有必要同時創(chuàng)建它們。此時有必要的是在文檔中為這些暫時不需要創(chuàng)建的對象設(shè)置一個開銷極小的代理對象。由它負責(zé)在需要時創(chuàng)建由它代理的主體對象。realsubjectrealsubjectrequest()clientproxyrequest() realsubject- request();subjectrequest()(a) 代理模式結(jié)構(gòu)aclientsubjectaproxyrealsubjectarealsubject(b)運行時刻的對象代理關(guān)系圖13.5 代理模式的結(jié)構(gòu)

17、和對象間的關(guān)系一般來說,在需要利用一個更通用的對象一般來說,在需要利用一個更通用的對象指針來代替較為專門化的對象指針的時候就指針來代替較為專門化的對象指針的時候就應(yīng)該使用代理模式。比如,除了以上所述的應(yīng)該使用代理模式。比如,除了以上所述的多媒體對象的代理外,還可以為不同地址空多媒體對象的代理外,還可以為不同地址空間的對象提供本地代理,為需要提供多種訪間的對象提供本地代理,為需要提供多種訪問權(quán)限的對象提供保護代理等等。問權(quán)限的對象提供保護代理等等。智能代理是代理模式的高級形式。智能代理是代理模式的高級形式。普通代理通過簡單的指針替換實現(xiàn)代理任務(wù),智能代理還可以在訪問被代理對象時執(zhí)行一些附加的操作

18、,如:在第一次引用一個持久對象時,將它裝入內(nèi)存;在訪問一個實際對象前,檢查它是否被加鎖,以防止沖突;對對象進行引用計數(shù)管理,當(dāng)對象不再被引用時自動將它釋放。智能代理的一種具體實現(xiàn)方式是重載智能代理的一種具體實現(xiàn)方式是重載c+的指針運算符的指針運算符-。這樣就可以在通。這樣就可以在通過指針訪問被代理對象時,執(zhí)行一些附過指針訪問被代理對象時,執(zhí)行一些附加的操作。加的操作。13.2.3 與對象行為相關(guān)的模式與對象行為相關(guān)的模式行為(行為(behavior)是指對象對請求的可預(yù)知是指對象對請求的可預(yù)知反應(yīng)。反應(yīng)。與對象行為相關(guān)的模式描述對象之間的通與對象行為相關(guān)的模式描述對象之間的通信關(guān)系,處理各種在

19、運行時難以跟蹤的復(fù)雜信關(guān)系,處理各種在運行時難以跟蹤的復(fù)雜控制流,描述一組對象怎樣相互協(xié)作以完成控制流,描述一組對象怎樣相互協(xié)作以完成其中任一對象都無法單獨完成的任務(wù)。其中任一對象都無法單獨完成的任務(wù)。5職責(zé)鏈(職責(zé)鏈(chain of responsibility)模式:)模式:職責(zé)鏈模式建立一些對象間的鏈接關(guān)系,使請求沿著該鏈傳遞,直到鏈上的某一個對象處理它為止。鏈上的多個對象都有機會接收和處理請求,從而避免請求的發(fā)送者和接收者之間的耦合關(guān)系。例如圖形用戶界面中的上下文有關(guān)幫助機制,用戶可在當(dāng)前界面以多種方式提交請求,啟動幫助。幫助信息窗口以含有進一步幫助的鏈接信息。這種鏈接式對象請求處理

20、通常從第一個接收請求的對象開始,或者自己處理該請求,或者轉(zhuǎn)發(fā)給鏈中下一個候選對象。 handlerrequest()concreat1request()concreat2request()clientsuccessor(a) 職責(zé)鏈結(jié)構(gòu)aclientahandleraconcreatsuccessoraconcreatsuccessor(b) 職責(zé)鏈對象鏈接圖13.6 職責(zé)鏈模式結(jié)構(gòu)及其對象結(jié)構(gòu)實現(xiàn)職責(zé)鏈的代碼示例:class handlerpublic:handler(handler* sp): successor(sp)virtual void request();private: han

21、dler* successor;這是一個事件處理句柄接口,其子類可以定義自己的request()實現(xiàn)?;惖娜笔崿F(xiàn)如下:virtual void handler:request() if (successor)successor- request();這是一個事先設(shè)定的固定的鏈,只要后繼存在就會無條件轉(zhuǎn)發(fā)。若在request()中用不同的請求參數(shù)來分派請求,可以實現(xiàn)更靈活的鏈接。void request(abstrctrequest* therequest) switch(therequest-getkind() case 1:request(abstrctrequest *) thereq

22、uest);break;case 2:/default:/break; 6命令(命令(command)模式)模式命令模式又稱事務(wù)(transaction)模式,命令模式用于封裝向某個對象的請求。所謂請求,就是應(yīng)用程序的操作人員通過圖形用戶界面(gui)構(gòu)件如按鈕、圖標(biāo)、菜單項等發(fā)出的操作命令。命令模式通過在請求調(diào)用對象和請求的執(zhí)行對象之間增加一個command中間對象,用以消解多對多復(fù)雜性。areceiverclientconcreatecommandexecute()areceiveaction()statecommandexecute()receiveraction()trigger clicked()acommandexecute()一個觸發(fā)器(ttri

溫馨提示

  • 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
  • 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
  • 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
  • 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
  • 5. 人人文庫網(wǎng)僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負責(zé)。
  • 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請與我們聯(lián)系,我們立即糾正。
  • 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時也不承擔(dān)用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。

評論

0/150

提交評論