Java裝飾器模式
- 摘要
- 實現
- 范例
-
裝飾器模式(Decorator Pattern)允許向一個現有的對象添加新的功能,同時又不改變其結構
-
裝飾器模式創建了一個裝飾類,用來包裝原有的類,并在保持類方法簽名完整性的前提下,提供了額外的功能
裝飾器模式屬于結構型模式,它是作為現有的類的一個包裝
摘要
1. 意圖
動態地給一個對象添加一些額外的職責。就增加功能來說,裝飾器模式相比生成子類更為靈活
2. 主要解決
一般的,我們為了擴展一個類經常使用繼承方式實現,由于繼承為類引入靜態特征,并且隨著擴展功能的增多,子類會很膨脹
3. 何時使用
- 在不想增加很多子類的情況下擴展類
4. 如何解決
將具體功能職責劃分,同時繼承裝飾者模式
5. 關鍵代碼
- Component類充當抽象角色,不應該具體實現;
- 修飾類引用和繼承Component類,具體擴展類重寫父類方法;
6. 應用實例
- 孫悟空有72變,當他變成”廟宇”后,他的根本還是一只猴子,但是他又有了廟宇的功能;
- 不論一幅畫有沒有畫框都可以掛在墻上,但是通常都是有畫框的,并且實際上是畫框被掛在墻上在掛在墻上之前,畫可以被蒙上玻璃,裝到框子里;這時畫、玻璃和畫框形成了一個物體;
7. 優點
- 裝飾類和被裝飾類可以獨立發展,不會相互耦合,裝飾模式是繼承的一個替代模式,裝飾模式可以動態擴展一個實現類的功能
8. 缺點
- 多層裝飾比較復雜
9. 使用場景
- 擴展一個類的功能;
- 動態增加功能,動態撤銷;
10. 注意事項
- 可代替繼承
實現
- 創建一個Shape接口和實現了Shape接口的實體類;
- 創建一個實現了Shape接口的抽象裝飾類ShapeDecorator,并把Shape對象作為它的實例變量;
- 創建類RedShapeDecorator實現了ShapeDecorator實體類;
- 創建類DecoratorPatternDemo使用RedShapeDecorator來裝飾Shape對象;
范例
我們通過下面的范例來演示裝飾器模式的用法,其中,我們將把一個形狀裝飾上不同的顏色,同時又不改變形狀類
1.創建一個接口.
Shape.java
package com.demo.gof;
public interface Shape {void draw();
}
2. 創建實現接口的實體類
Rectangle.java
package com.demo.gof;
public class Rectangle implements Shape {@Overridepublic void draw() {System.out.println("Shape: Rectangle");}
}
Circle.java
package com.demo.gof;
public class Circle implements Shape {@Overridepublic void draw() {System.out.println("Shape: Circle");}
}
3. 創建實現了 Shape 接口的抽象裝飾類
ShapeDecorator.java
package com.demo.gof;
public abstract class ShapeDecorator implements Shape {protected Shape decoratedShape;public ShapeDecorator(Shape decoratedShape){this.decoratedShape = decoratedShape;}public void draw(){decoratedShape.draw();}
}
4. 創建擴展了 ShapeDecorator 類的實體裝飾類
RedShapeDecorator.java
package com.demo.gof;
public class RedShapeDecorator extends ShapeDecorator {public RedShapeDecorator(Shape decoratedShape) {super(decoratedShape); }@Overridepublic void draw() {decoratedShape.draw(); setRedBorder(decoratedShape);}private void setRedBorder(Shape decoratedShape){System.out.println("Border Color: Red");}
}
5. 使用 RedShapeDecorator 來裝飾 Shape 對象
DecoratorPatternDemo.java
package com.demo.gof;
public class DecoratorPatternDemo {public static void main(String[] args) {Shape circle = new Circle();Shape redCircle = new RedShapeDecorator(new Circle());Shape redRectangle = new RedShapeDecorator(new Rectangle());System.out.println("Circle with normal border");circle.draw();System.out.println("\nCircle of red border");redCircle.draw();System.out.println("\nRectangle of red border");redRectangle.draw();}
}
編譯運行以上 Java 范例,輸出結果如下
$ javac -d . src/main/com.demo/gof/DecoratorPatternDemo.java
$ java com.demo.gof.DecoratorPatternDemo
Circle with normal border
Shape: CircleCircle of red border
Shape: Circle
Border Color: RedRectangle of red border
Shape: Rectangle
Border Color: Red