定義
裝飾器模式(Decorator Pattern)允許向一個(gè)現(xiàn)有的對(duì)象添加新的功能,同時(shí)又不改變其結(jié)構(gòu)。這種類(lèi)型的設(shè)計(jì)模式屬于結(jié)構(gòu)型模式,它是作為現(xiàn)有的類(lèi)的一個(gè)包裝
裝飾器模式是對(duì)象結(jié)構(gòu)動(dòng)態(tài)修改方式,相較于繼承關(guān)系,裝飾器更加靈活,和代理模式相比,裝飾器模式更偏重與對(duì)象本質(zhì)行為或者屬性的加強(qiáng),比如窗口系統(tǒng)添加主題。而代理模式則更偏重于非本質(zhì)行為的添加,比如文件系統(tǒng)中添加權(quán)限管理和修改日志。
實(shí)例
public interface Shape {
void draw();
}
public class Circle implements Shape {
@Override
public void draw() {
System.out.println("Shape: Circle");
}
}
public class Rectangle implements Shape {
@Override
public void draw() {
System.out.println("Shape: Rectangle");
}
}
public class RedShapeDecorator extends ShapeDecorator {
public RedShapeDecorator(Shape decoratedShape) {
super(decoratedShape);
}
@Override
public void draw() {
decoratedShape.draw();
setRedBorder(decoratedShape);
}
private void setRedBorder(Shape decoratedShape){
System.out.println("Border Color: Red");
}
}
public abstract class ShapeDecorator implements Shape {
protected Shape decoratedShape;
public ShapeDecorator(Shape decoratedShape){
this.decoratedShape = decoratedShape;
}
public void draw(){
decoratedShape.draw();
}
}
其類(lèi)圖關(guān)系為:
UML
上述是給Shape實(shí)例添加邊框的實(shí)例,從功能角度出發(fā),使用繼承并重寫(xiě)draw方法就可以實(shí)現(xiàn)邊框,只是有多少個(gè)需要邊框的shape子類(lèi),就需要重寫(xiě)多少個(gè)類(lèi),這樣類(lèi)的數(shù)量很容易會(huì)爆炸,而采用包裝器模式,保持該包裝器職責(zé)單一,這里RedShapeDecorator類(lèi)只負(fù)責(zé)添加紅色邊框(實(shí)際上不應(yīng)該硬編碼為紅色),如果Circle類(lèi)需要邊框,也可以直接用RedShapeDecorator包裝一下就行,而且多個(gè)包裝器可以相互組合包裝,能組合出復(fù)雜的功能。
總結(jié)
優(yōu)點(diǎn):
- 裝飾類(lèi)和被裝飾類(lèi)是可以獨(dú)立的,低耦合的?;ハ喽疾挥弥缹?duì)方的存在
- 裝飾模式是繼承的一種替代方案,無(wú)論包裝多少層,返回的對(duì)象都是is-a的關(guān)系(上面的例子:包裝完還是Phone類(lèi)型)。
- 實(shí)現(xiàn)動(dòng)態(tài)擴(kuò)展,只要繼承了裝飾器就可以動(dòng)態(tài)擴(kuò)展想要的功能了。
缺點(diǎn):
- 多層裝飾是比較復(fù)雜的,提高了系統(tǒng)的復(fù)雜度。不利于我們調(diào)試
在Java中,對(duì)類(lèi)功能增強(qiáng)的方式三種:
- 繼承:重寫(xiě)或者修改類(lèi)原有行為和屬性
- 代理模式:主要用于增加類(lèi)非本質(zhì)功能和屬性,其本質(zhì)上不是增強(qiáng)類(lèi)原有功能,而是增加類(lèi)非本質(zhì)功能
- 包裝器模式: 主要用于增強(qiáng)類(lèi)本質(zhì)功能和屬性,其本質(zhì)是增強(qiáng)類(lèi)原有能力