装饰模式/Decorator

装饰模式/Decorator

意图/适用场景:

装饰模式将更多的功能动态地附加到一个对象上。对功能扩展而言,装饰模式提供了一个灵活的、可以替代“继承”的选择。

装饰模式通过被装饰类的一个子类的实例,把客户端的调用委派到被装饰类。

在以下情况下应当使用装饰模式:

  1. 需要扩展一个类的功能,或给一个类增加责任。
  2. 需要动态地给一个对象增加功能,这些功能可以再动态地撤销。
  3. 需要增加同一些基本功能的排列组合而产生的非常大量的功能,从而使继承关系变得不现实。

UML:

装饰模式/Decorator

参与者:

  1. Component: 一个抽象接口,规范了准备接收附加功能/责任的对象。
  2. Concrete Component: 定义一个将要接收附加功能/责任的类。
  3. Decorator: 持有一个Component对象的实例,并且实现Component接口。在实现的接口方法中,调用Component对象的相应方法来实现功能。
  4. Concrete Decorator: 负责给Component对象附加功能。

要点:

Decorator模式的设计思想在于,系统中会有很多个Concrete Decorator,而每一个Concrete Decorator可以把其它的Concrete Decorator作为自己的基础,在其之上增加一些功能。

而这些功能扩展是动态的,而且是多变的,各种Concrete Decorator可以随意地互相组合。这不同于基于继承的扩展,后者是静态的、不变的。

优点与缺点:

  1. 装饰模式与继承关系的目的都是扩展对象的功能,但装饰模式可以提供更多的灵活性。
  2. 通过使用不同的Concrete Decorator以及它们的组合,可以创造出很多不同行为的组合。
  3. 使用装饰模式比使用继承关系需要的类数目更少,但对象的数目会更多,而且对象间的组合关系会更加复杂。

扩展:

看下面的这幅对象关系图。这是Decorator模式的典型用法,对象的数量还可以更多,层数也可以更多。在每一层,Concrete Decorator对下一层的功能做一点扩展,最后实现了庞大的功能集合。 也可以这样理解,Concrete Component被一层一层的Concrete Decorator所包裹,所以这种模式也常常被称为“包裹”模式。

示例代码:

[java]
// Source code from file:  Component.java

package designPatterns.Decorator;

public interface Component {
public void sampleOperation();
}

// Source code from file:  ConcreteComponent.java

package designPatterns.Decorator;

public class ConcreteComponent implements Component {

public void sampleOperation() {
System.out.println("ConcreteComponent.sampleOperation()");
}

}

// Source code from file:  ConcreteDecoratorA.java

package designPatterns.Decorator;

public class ConcreteDecoratorA extends Decorator {

private Decorator decorator;

public ConcreteDecoratorA() {
this.decorator null;
}

public ConcreteDecoratorA(Decorator decorator) {
this.decorator = decorator;
}

public void sampleOperation() {
System.out.println("ConcreteDecoratorA.sampleOperation()");
if (null != decorator)
decorator.sampleOperation();
}
}

// Source code from file:  ConcreteDecoratorB.java

package designPatterns.Decorator;

public class ConcreteDecoratorB extends Decorator {

private Decorator decorator;

public ConcreteDecoratorB() {
this.decorator null;
}

public ConcreteDecoratorB(Decorator decorator) {
this.decorator = decorator;
}

public void sampleOperation() {
System.out.println("ConcreteDecoratorB.sampleOperation()");
if (null != decorator)
decorator.sampleOperation();
}
}

// Source code from file:  Decorator.java

package designPatterns.Decorator;

public class Decorator implements Component {

private Component component;

public Decorator() {
// make a default component;
component = new ConcreteComponent();
}

public Decorator(Component component) {
this.component = component;
}

public void sampleOperation() {
System.out.println("Decorator.sampleOperation()");
component.sampleOperation();
}

}

// Source code from file:  User.java

package designPatterns.Decorator;

public class User {
public static void main(String[] args) {
Component c = new ConcreteComponent();
Decorator decorator = new Decorator(c);
Decorator a = new ConcreteDecoratorA(decorator);
Decorator b = new ConcreteDecoratorB(a);
b.sampleOperation();

System.out.println();

// re-org
b = new ConcreteDecoratorB(decorator);
a = new ConcreteDecoratorA(b);
a.sampleOperation();
}
}
[/java]
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值