装饰者设计模式----IO流
Java装饰模式
装饰模式:给一个类添加一些额外的职责,并且在添加这些额外的职责时不会控制该类的执行逻辑。 装饰模式以对客户端透明的方式扩展对象的功能,是继承关系的一个替代方案。
装饰模式以对客户端透明的方式动态的给一个对象附加上更多的责任。换言之客户端并不会觉的对象在装饰前和装饰后有什么区别。
实例化 装饰者子类的时候,是调用构建者子类来实例化,不会调用装饰者类,装饰者类对客户端来说是透明的,只是对功能的扩张。
UML类图:
装饰模式与类继承的区别
1: 装饰模式是一种动态行为,对已经存在类进行随意组合,而类的继承是一种静态的行为,一个类定义成什么样的,该类的对象便具有什么样的功能,无法动态的改变。
2: 装饰模式扩展的是对象的功能,不需要增加类的数量,而类继承扩展是类的功能,在继承的关系中,如果我们想增加一个对象的功能,我们只能通过继承关系,在子类中增加两个方法。
3: 装饰模式是在不改变原类文件和使用继承的情况下,动态的扩展一个对象的功能,它是通过创建一个包装对象,也就是装饰来包裹真是的对象。
组成部分:
抽象构件:原始的功能接口-----相当于i/o流里面InputStream/OutputStream和Reader/Writer。
具体构件:具体的原始功能类----实现接口的类---------------相当于i/o里面的FileOutputStream和FileInputStream。
装饰角色:持有具体构件类的对象,以便执行原有功能------接口的实现类,类里调用接口的对象 --------------相当于i/o里面的FilerOutputStream和FilterInputStream。
具体装饰:具体扩展的功能在这里--------------------------------相当于i/o流里面的BufferedOutputStream和BufferedInputStream以及DataOutputStream和DataInputSrtream。
接口--抽象构建类:
1 /** 2 * 抽象接口,规范准备接收附加责任的对象 3 * @author gjy 4 */ 5 public interface Component { 6 public void operation(); 7 }
接口实现类--具体构建:
1 package com.gjy.drector; 2 3 /** 4 * 接收附加责任, 此类型的类可以有多个, 只对应一个Decorator类 5 * @author gjy 6 */ 7 public class ConcreteComponent implements Component { 8 public ConcreteComponent(){} 9 public void operation() 10 { 11 System.out.println("开车"); 12 } 13 }
接口另一个实现类--装饰者:
装饰者:构造方法:创建接口对象。方法:通过接口对象调用实现类覆写接口的方法
1 package com.gjy.drector; 2 3 /** 4 * 装饰角色,持有一个构件(Component)对象的实例,并定义一个与抽象构件接口一致的接口 5 * @author gjy 6 */ 7 public class Decorator implements Component { 8 private Component component; 9 public Decorator(){} 10 11 public Decorator(Component component) 12 { 13 this.component = component; 14 } 15 16 public void operation() { 17 component.operation(); 18 } 19 }
装饰者子类:继承装饰者类,扩展其功能,构造方法:返回接口对象
1 package com.gjy.drector; 2 3 /** 4 * 添加附加责任 5 * @author gjy 6 */ 7 public class ConcreteDecorator extends Decorator { 8 9 public ConcreteDecorator(){} 10 11 public ConcreteDecorator(Component component) 12 { 13 super(component); 14 } 15 16 public void operation() 17 { 18 this.addedOperation(); 19 super.operation(); 20 } 21 22 public void addedOperation() 23 { 24 System.out.println("晚上"); 25 } 26 }
测试主函数:
1 package com.gjy.drector; 2 3 /** 4 * 客户端类 5 * @author gjy 6 */ 7 8 public class Client { 9 public static void main(String[] args) { 10 Component component = new ConcreteComponent(); 11 Decorator decorator = new ConcreteDecorator(component); 12 //客户端不变, 但已增加了责任 13 decorator.operation(); 14 15 } 16 }
1 Component component = new ConcreteDecorator(new Decorator(new ConcreteComponent()));
实际上--装饰者类不应该实例化,实例化的是它的子类。
1 ConcreteDecorator concreteDecorator=new ConcreteDecorator(new ConcreteComponent()); 2 concreteDecorator.operation();
在java IO中
DataoutputStream out=new DataoutputStream(new FileoutputStream());
这就是 装饰者模式,DataoutputStream是装饰者子类,FileoutputStream是实现接口的子类。
这里不会调用到装饰者类--FilteroutputStream,只是作为继承的另一种方案,对客户端来说是透明的,是为了功能的扩张.
输出结果:
晚上
开车
其实装饰者就是给对象穿马甲 多穿一层就多加一点功能