[英]Calling non-decorated methods on decorator object
假設我們已經實現了裝飾器模式 ,如下圖所示。 使用CondimentDecorator類,可以裝飾Beverage類。 方法cost()
和getDescription()
會注意這一點。
當創建如下所示的裝飾飲料時 ,調用方法getName()不適用於裝飾對象。 為了完成這項工作,還應該將該方法放在CondimentDecorator類中,並將調用委托給組合的Drink變量。
Beverage b = new Milk(new Espresso("A very nice espresso"));
b.getName() // returns null
當有很多不需要修飾的方法時,所有這些方法也都應該放在CondimentDecorator中以簡單地委派。 因此問題是: 解決此“問題”的一種整潔(通常被接受)的方法是什么?
對於像Java或C#這樣的靜態類型語言(是的,C#不是完全靜態類型的,我知道DLR和動態的),這種“問題”的普遍接受的方法是讓裝飾方法明確地委派給裝飾對象。 該解決方案具有簡單和顯明顯的利益。
在您的示例中,如果不重寫getName
則意味着您要更改裝飾對象的行為,這正是裝飾器模式的目的。
如果您選擇默認情況下委托給裝飾對象,則它看起來好像繼承已中斷,因為CondimentDecorator繼承自Beverage,但未使用基類的方法。
然后,要更改此行為,您將需要以某種方式定義未委托給裝飾對象的方法,但應“照常繼承”工作。 那將是不明顯的並且非常混亂。
話雖如此,您想要實現的目標應該可以在Java中實現。
例如,在.NET中,您可以通過以下方式進行操作,我相信Java具有類似的功能
此外,請檢查原型繼承在JavaScript中的工作方式-該行為與您要實現的行為非常相似
在您的情況下,如果只有幾個operation1(),可以將委托調用添加到CondimentDecorator。 如果只有很少的call()需要裝飾,則可以在需要時制作裝飾器,例如:DecoratorFactory.make(new Milk(new Espresso(“ Espresso”)))。getDescription();
要么
CondimentDecorator.getDescription(new Milk(new Espresso(“ A a great nice espresso”))));
重點:模式為您服務。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.