装饰模式是一种对象结构型模式,它可以在不改变一个类本来的工作职责的情况下,动态的添加新的功能
装饰者模式的结构
1.**Component(抽象构件):**它是具体类和抽象类的装饰类的共同的父类
2.**ConcreteComponent(具体构件):**它是抽象构件的具体实现子类,是我们会真正使用到功能的类,可以被装饰类动态添加职责
3.**Decorator(抽象类):**他也是抽象构件的子类,而且内聚了一个抽象构件对象,这个对象可以调用装饰之前构件中对象的方法,并通过其子类扩展该方法,以达到装饰的目的
4.**ConcreteDecorate(具体装饰类):**它是抽象装饰类的子类,负责向构件添加新的职责
下面是一个案例:
某软件公司基于面向对象技术开发了一套图形界面构件库,该构件库提供给了大量的基本构建,如窗体,文本框,列表框等,由于在使用该构建库时用户经常要求定义一些特殊的显示效果,如带滚动条的窗体,带黑色边框的文本框,即带滚动条又带黑色边框的列表框等。因此经常需要对构件库进行扩展以增强其功能
Component抽象构件角色:是后面所有对象的父类
package com.designpatten.decorator.demo1;
public abstract class Component {
public abstract void display();
}
ConcreteComponent:具体的构件,真正用于工作的类
package com.designpatten.decorator.demo1;
public class Window extends Component {
@Override
public void display() {
System.out.println("我是窗体");
}
}
package com.designpatten.decorator.demo1;
public class TextBox extends Component {
@Override
public void display() {
System.out.println("我是文本框");
}
}
package com.designpatten.decorator.demo1;
public class ListBox extends Component {
@Override
public void display() {
System.out.println("我是列表框");
}
}
Decorator抽象的装饰类:内部内聚了一个Component对象,用于真实工作
package com.designpatten.decorator.demo1;
public class ComponentDecorator extends Component {
protected Component component;
public ComponentDecorator() {
}
public ComponentDecorator(Component component) {
this.component = component;
}
public void setComponent(Component component) {
this.component = component;
}
@Override
public void display() {
component.display();
}
}
**ConcreteDecorate具体装饰类:**继承了Decorate类,具体的用于装饰的对象
package com.designpatten.decorator.demo1;
public class BlackBorderDecorator extends ComponentDecorator {
public BlackBorderDecorator(Component component) {
super(component);
}
public BlackBorderDecorator() {
}
@Override
public void display() {
this.setBlackBorder();
super.display();
}
private void setBlackBorder() {
System.out.println("设置黑色的边框");
}
}
package com.designpatten.decorator.demo1;
public class ScrollBarDecorator extends ComponentDecorator {
public ScrollBarDecorator(Component component) {
super(component);
}
@Override
public void display() {
this.setScrollBar();
super.display();
}
private void setScrollBar() {
System.out.println("为构件添加滚动条");
}
}
客户端类
package com.designpatten.decorator.demo1;
import java.util.List;
public class Client {
public static void main(String[] args) {
Component component = new ListBox();
component = new ScrollBarDecorator(component);
component = new BlackBorderDecorator(component);
component.display();
}
}
执行结果
可以看出客户端创建了一个黑色边框的对象,然后可以很轻松的为这个黑色边框对象添加滚动条,列表框。可以在不改变黑色边框本身功能的前提下添加新的职责
装饰模式的优点
1.易于扩展一个对象的功能,装饰模式比继承更加灵活,不会导致类的个数急剧上升。
2.可以通过一种动态的方式来扩展一个对象的功能,可以使对象的功能变的更强大
3.具体的构建类与具体的装饰类可以自由组合,用户可以根据自己的需要去添加新的装饰类
装饰模式的缺点
1.在使用装饰模式进行系统的设计的时候,会产生很多的小对象,这些小对象有些时候知识他们之间的连接方式不同,有很多部分是相同的,大量的小对象会占用系统的资源,在一定程度上会影响程序的性能
2.对于多次装饰的对象,它比起继承更加容易出错,排错也更加的困难