装饰者模式 - 结构型模式

个人理解:    

模式类型:

    Decorator 装饰者模式 - 结构型模式

概述:

    The intent of this pattern is to add additional responsibilities dynamically to an object.
    动态地将责任附加到对象上,若要扩展对象,装饰者模式提供了比继承更弹性的替代方案。


角色:
Component(被装饰对象基类)
    定义对象的接口,可以给这些对象动态增加职责;
ConcreteComponent(具体被装饰对象)
    定义具体的对象,Decorator可以给它增加额外的职责;
Decorator(装饰者抽象类)
    维护一个指向Component实例的引用,并且定义了与Component一致的接口;
ConcreteDecorator(具体装饰者)
    具体的装饰对象,给内部持有的具体被装饰对象增加具体的职责;
    
模式的应用场景:
    1、  想透明并且动态地给对象增加新的职责的时候。
    2、  给对象增加的职责,在未来存在增加或减少可能。
    3、  用继承扩展功能不太现实的情况下,应该考虑用组合的方式。

结构图:
装饰者模式 - 结构型模式_第1张图片


模式的优缺点:

    装饰者模式的优点:
    1、  通过组合而非继承的方式,实现了动态扩展对象的功能的能力。
    2、  有效避免了使用继承的方式扩展对象功能而带来的灵活性差,子类无限制扩张的问题。
    3、  充分利用了继承和组合的长处和短处,在灵活性和扩展性之间找到完美的平衡点。
    4、  装饰者和被装饰者之间虽然都是同一类型,但是它们彼此是完全独立并可以各自独立任意改变的。
    5、  遵守大部分GRASP原则和常用设计原则,高内聚、低偶合。    
    装饰者模式的缺点:
    1、  装饰链不能过长,否则会影响效率。
    2、  因为所有对象都是继承于Component,所以如果Component内部结构发生改变,则不可避免地影响所有子类(装饰者和被装饰者),也就是说,通过继承建立的关系总是脆弱地,如果基类改变,势必影响对象的内部,而通过组合(Decoator HAS A Component)建立的关系只会影响被装饰对象的外部特征。
    3、只在必要的时候使用装饰者模式,否则会提高程序的复杂性,增加系统维护难度。


模式的应用实例:
    在java的io类中,在OutputStream,InputStream,Reader,Writer等都用到了Decorator模式

在java IO中:

DataoutputStream out=new DataoutputStream(new FileoutputStream());

这就是 装饰者模式,DataoutputStream是装饰者子类,FileoutputStream是实现接口的子类。


要点:
1. 装饰者和被装饰对象有相同的超类型。
2. 可以用一个或多个装饰者包装一个对象。
3. 装饰者可以在所委托被装饰者的行为之前或之后,加上自己的行为,以达到特定的目的。
4. 对象可以在任何时候被装饰,所以可以在运行时动态的,不限量的用你喜欢的装饰者来装饰对象。
5. 装饰模式中使用继承的关键是想达到装饰者和被装饰对象的类型匹配,而不是获得其行为。
6. 装饰者一般对组件的客户是透明的,除非客户程序依赖于组件的具体类型。在实际项目中可以根据需要为装饰者添加新的行为,做到“半透明”装饰者。
7. 适配器模式的用意是改变对象的接口而不一定改变对象的性能,而装饰模式的用意是保持接口并增加对象的职责。



代码(其实读UML图要比代码还要一目了然)
interface Sourcable {    
    public void operation();  
}   
class Source implements Sourcable {    
    public void operation() {    
        System.out.println("原始类的方法");    
    }    
}
class Decorator1 implements Sourcable {    
    private Sourcable sourcable;    
    public Decorator1(Sourcable sourcable){    
        super();    
        this.sourcable=sourcable;    
    }    
    public void operation() {    
        System.out.println("第一个装饰器前");    
        sourcable.operation();    
        System.out.println("第一个装饰器后");    
    }  
}   
class Decorator2 implements Sourcable {    
    private Sourcable sourcable;    
    public Decorator2(Sourcable sourcable){    
        super();    
        this.sourcable=sourcable;    
    }    
    public void operation() {    
        System.out.println("第二个装饰器前");    
        sourcable.operation();    
        System.out.println("第二个装饰器后");    
    }    
}  
class Decorator3 implements Sourcable {    
    private Sourcable sourcable;    
    public Decorator3(Sourcable sourcable){    
        super();    
        this.sourcable=sourcable;    
    }    
    public void operation() {    
        System.out.println("第三个装饰器前");    
        sourcable.operation();    
        System.out.println("第三个装饰器后");    
    }    
}   
public class Test {  
    /**
     * @param args
     */  
    public static void main(String[] args) {  
        Sourcable source = new Source();  
        // 装饰类对象   
        Sourcable obj = new Decorator1(new Decorator2(new Decorator3(source)));  
        obj.operation();  
    }  
}  



运行该程序的输出如下:
第一个装饰器前
第二个装饰器前
第三个装饰器前
原始类的方法
第三个装饰器后
第二个装饰器后
第一个装饰器后  
 
从输出的结果可以看出,原始类对象source 依次被 Decorator1 、 Decorator2 、 Decorator3 进行了装饰。   


所有模式

     创建型模式,共五种:工厂方法模式、抽象工厂模式、单例模式、建造者模式、原型模式。
结构型模式,共七种:适配器模式、装饰器模式、代理模式、外观模式、桥接模式、组合模式、享元模式。
    行为型模式,共十一种:策略模式、模板方法模式、观察者模式、迭代子模式、责任链模式、命令模式、备忘录模式、状态模式、访问者模式、中介者模式、解释器模式。
    补充模式:空对象模式

参考/转自:
http://www.cnblogs.com/god_bless_you/archive/2010/06/10/1755212.html
http://www.cnblogs.com/rush/archive/2011/05/08/Decorator_DesignPattern_NETFramework.html
http://blog.chinaunix.net/uid-20761674-id-304542.html



转载请注明:http://blog.csdn.net/paincupid/article/details/44038877


你可能感兴趣的:(设计模式,Decorator,装饰者模式,行为模式)