裝飾者模式就是實現一些被裝飾者主體,之後由若干了裝飾者方法可以對被裝飾者進行動態裝飾。通過使用組合的方式,避免使用繼承。可以動態擴充,相對靈活,但是缺點是實現的類比較多。
Componet 裝飾者模式就是定義一個被裝飾者的基類,實現一些被裝飾者的行為,之後實現具體的被裝飾者對象。
Decorator在被裝飾者的基類的基礎上實現裝飾者基類,裝飾者基類要繼承被裝飾者的基類,此基類實現了裝飾者要實現的接口。對可對原有接口就行修改。
之後實現具體的裝飾者,其保存了需要裝飾的被裝飾者實體對象,之後調用方法對裝飾者進行裝飾。
下面以一個簡單的例子來實現裝飾者模式,首先定義一個被裝飾者基類為人。
之後實現各個被裝飾者實體為遼寧人或山東人等。
在後定義一個裝飾者基類,繼承被裝飾者基類,並可以對其接口進行修改。規范裝飾者實體對象所要實現的行為。
最後定義具體的裝飾者,其保存了要裝飾的實體對象,並實現對被裝飾者的裝飾。
代碼如下:
被裝飾者虛基類
/** 被裝飾者虛基類 **/ class CHuman { public: //這裡Info信息是被裝飾者的虛函數,但是裝飾者 //想要修改此方法時,可以通過裝飾者的虛基類繼承被 //裝飾者的虛基類並重新實現其原有方法 virtual string Info() { m_sInfo = "沒有任何信息"; return m_sInfo; } //存虛函數,派生類必須實現 virtual int Leavl() = 0; protected: string m_sInfo; };
被裝飾者具體實現類 遼寧人
/** 被裝飾者具體實現類 **/ class CLiaoningHuman :public CHuman { public: CLiaoningHuman() { m_sInfo = "遼寧人"; } virtual int Leavl() { return 0; } };
被裝飾者具體實現類 山東人
/** 被裝飾者具體實現類 **/ class CShanDongHuman :public CHuman { public: CShanDongHuman() { m_sInfo = "山東人"; } virtual int Leavl() { return 0; } };
裝飾者虛基類
/** 裝飾者虛基類,定義了裝飾者具體對象 所要必須實現的接口,並對被裝飾者的基類 接口進行修改 **/ class Decorator:public CHuman { public: /** 繼承了被裝飾者的主要接口,並對需要修改的接口 進行修改,覆蓋了被裝飾紙的Info接口,並在具體裝飾者 對象上具體實現 **/ virtual string Info() = 0; };
裝飾者實體對象 武當武功
/** 裝飾者實現具體類 **/ class CDecratorWuDang : public Decorator { public: CDecratorWuDang(CHuman *pCHuman) { m_pCHuman = pCHuman; } //實現裝飾者基類的存虛函數 (此接口修改了被裝飾者的虛基類接口) virtual string Info() { return m_pCHuman->Info() + " 學習了武當功夫 "; } virtual int Leavl() { return m_pCHuman->Leavl() + 1; } private: //保存具體的被裝飾者對象 CHuman *m_pCHuman; };
裝飾者實體對象 少林武功
/** 裝飾者實現具體類 **/ class CDecratorShaoLin : public Decorator { public: CDecratorShaoLin(CHuman *pCHuman) { m_pCHuman = pCHuman; } //實現裝飾者基類的存虛函數 (此接口修改了被裝飾者的虛基類接口) virtual string Info() { return m_pCHuman->Info() + " 學習了少林功夫 "; } virtual int Leavl() { return m_pCHuman->Leavl() + 2; } private: //保存具體的被裝飾者對象 CHuman *m_pCHuman; };
裝飾者實體對象 華山武功
/** 裝飾者實現具體類 **/ class CDecratorShaoLin : public Decorator { public: CDecratorShaoLin(CHuman *pCHuman) { m_pCHuman = pCHuman; } //實現裝飾者基類的存虛函數 (此接口修改了被裝飾者的虛基類接口) virtual string Info() { return m_pCHuman->Info() + " 學習了少林功夫 "; } virtual int Leavl() { return m_pCHuman->Leavl() + 2; } private: //保存具體的被裝飾者對象 CHuman *m_pCHuman; };
測試函數
int main(int argc, char* argv[]) { //定義被裝飾者實體對象 CHuman *pCHuman = new CLiaoningHuman(); //定義裝飾者,並將被裝飾者傳入對其進行裝飾 pCHuman = new CDecratorWuDang(pCHuman); pCHuman = new CDecratorShaoLin(pCHuman); pCHuman = new CDecratorHuaShan(pCHuman); cout<<pCHuman->Info()<<endl; cout<<pCHuman->Leavl()<<endl; pCHuman = new CShanDongHuman(); pCHuman = new CDecratorWuDang(pCHuman); pCHuman = new CDecratorShaoLin(pCHuman); cout<<pCHuman->Info()<<endl; cout<<pCHuman->Leavl()<<endl; cout<<endl<<"Press any key exit....."<<endl; char c=getchar(); c=getchar(); return 0; }
測試結果
本文出自 “風清揚song” 博客,請務必保留此出處http://2309998.blog.51cto.com/2299998/1291015