作者TKB5566 (蔡英文還我七天假!!)
看板java
標題Re: [問題] 裝飾者模式的原理
時間Sun Apr 16 19:04:36 2023
目前對裝飾者模式產生的原因理解如下:
若以人穿衣服,或是飲料店對飲料加料為例,人跟飲料可以是最上層的父類別
衣服可以有很多種,飲料要加的料也可以有很多種,若是以繼承的方式來給人穿衣服
或是給飲料加料,這樣的話:
人+一種衣服是一種子類別,飲料+一種料也是一種子類別。
這樣的話很多種衣服很多種料,就會有很多種子類別。
更不要說很多種衣服、很多種料各自還可以組合出不同子類別。
所以很明顯,子類別數量會過於龐大。
而且人+一種衣服、飲料+一種料,按照邏輯,衣服跟料都是可選擇的,順序不固定的,
若用繼承方式去擴充人和飲料的話,那就是
把穿衣服跟加料的順序寫死。這就完全
不符合人類穿衣或給飲料加料的邏輯,也就是說完全不合理。
這是一個原因。
另一個原因,以麥當勞主餐配副餐,組成套餐為例。主餐配副餐形成套餐,
看似可以用繼承方式來描述,也就是主餐為父類別,套餐繼承主餐類別並加上副餐,
形成子類別。但是
主餐往往不只一種,這樣的話變成
有多種主餐,套餐要繼承主餐就會變成是多重繼承。
因此在某些需求下,會變成多重繼承,這是Java程式必須避免的現象。
再來,若是堅持要以繼承來實作以上的例子,繼承可能會有很多層,例如飲料加了
很多料,其實就是子類別有好幾層,下一層類別都包含了上一層類別,這樣的話,
若是要計算「加了很多料的飲料」的價格,
計算的method必須層層呼叫到最上層的類別,
取出原始飲料的價格後,又層層返回到最下層的,加了很多料的類別,這樣才能計算出
「加了很多料的飲料」的價格,也就是說類別之間相依性很高,而相依性高正好也是
Java程式必須避免的問題。
-----------------------------------
所以總結以上的說法,可以歸納出使用繼承來給類別擴充功能,會有三個問題:
1
子類別擴充順序是寫死的,這樣要把所有擴充順序都列出,子類別會過多。
2
單一繼承不能處理所有需求,變成不得不多重繼承。
3
程式之間相依性過高。
-----------------------------------
為了解決使用繼承來給類別擴充功能,所帶來的三個問題,就希望可以:
針對第1個問題,給類別擴充功能必須可以依需求來調整擴充的順序。
針對第2個問題,做到不使用多重繼承也能做出多重繼承的效果;
而介面正好可以多重實作,所以這裡可以考慮以介面代替類別來進行實作。
針對第3個問題,就是要降低類別之間的相依性,這也可以藉由介面來實現。
於是裝飾者模式,就這樣被設計出來了。
--
※ 發信站: 批踢踢實業坊(ptt.cc), 來自: 49.216.165.102 (臺灣)
※ 文章網址: https://webptt.com/m.aspx?n=bbs/java/M.1681643078.A.A30.html
1F:推 brt: 很清楚 04/22 10:41
2F:推 thewindjuei: 感謝分享說明 04/28 12:41