設計模式推演——裝飾已有對象(Proxy/Decorator)

上一篇文章中,我們提到OO中複用的方式有兩種,組合和繼承。一般情況下,應該儘可能使用組合的方式。現在以複用爲基本需求,推演若干常見組合型模式



1. Decorator模式

 需求:我們已經有一羣對象,現在想統一爲這些對象添加若干新特性。更重要的是,這些新特性可以反覆疊加於某個對象,或者只選擇部分特性作用於某個對象

條件:如果這個特性的實現不依賴於具體的對象,就如同添加一個裝飾,那麼可以應用Decorator模式。

如果基於開閉原則出發,實際上就是要求不修改已有的對象,通過爲每一個新特性實現一個Decorator類來實現擴展(使用的方式是組合)。

應該說:Decorator的使用條件是異常苛刻的,因爲每一個Decorator類要求可裝飾於任意的對象,這些對象可以是現在已經存在的,同時包括那些未來時的。




2. Proxy模式

Proxy模式有點類似於Decorator模式,也是爲已有類的行爲做些新的裝飾。所不同的是,Proxy模式一般只是爲一個對象作裝飾,且這些裝飾不會相互組合疊加

從開閉原則出發,Proxy與Decorator模式相同,都是要求不修改已有的對象,通過組合的方式,新建一個Proxy類來擴展原有對象的功能。


Proxy模式是典型的中間層技術,以Proxy對象作爲中間層,代替原始對象,從而提供一種更靈活的設計方式。

對代理模式,常見的應用情景是權限和訪問控制:

1) 遠程代理(Remote  Proxy)爲一個位於不同的地址空間的對象提供一個本地的代理對象。這個不同的地址空間可以是在同一臺主機中,也可是在另一臺主機中,遠程代理又叫做大使(Ambassador)。
2) 虛擬代理(Virtual Proxy)根據需要創建開銷很大的對象。如果需要創建一個資源消耗較大的對象,先創建一個消耗相對較小的對象來表示,真實對象只在需要時纔會被真正創建。 
3) 保護代理(Protection Proxy)控制對原始對象的訪問。保護代理用於對象應該有不同的訪問權限的時候。
4) 智能指引(Smart Reference)取代了簡單的指針,它在訪問對象時執行一些附加操作。
5) Copy-on-Write代理:它是虛擬代理的一種,把複製(克隆)操作延遲到只有在客戶端真正需要時才執行。


3.  Decorator模式 /Proxy模式與重構

如果原始代碼沒有使用Decorator模式 /Proxy模式,那麼大多數情況下基本是使用了繼承+多態的方式實現,就這種情況而言,可以使用Replace Inheritance with Delegate重構方法。



最後想說明的是,

1. 這兩個模式的應用時機

雖然這兩個模式是都是裝飾已有對象的行爲,但是一般設計之初我們可能就已經有意的引入這兩個模式。

2. 爲什麼不是多態,而是組合

首先,使用多態總是可以實現需求的,但正如之前文章中所論述的,應該儘可能使用組合。

第二,這兩個模式的主要特點是裝飾,通過裝飾,將對象的主要行爲由原始對象體現,將對象的一些別緻行爲由裝飾對象或者代理對象實現。

這樣的設計更滿足單一職責原則。

3. 爲什麼說是裝飾已有行爲?

沒有增加新的接口;改變了原有接口的效果;




發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章