设计模式之装饰者模式

定义:
装饰模式指的是在不必改变原类文件和使用继承的情况下,动态地扩展一个对象的功能。它是通过创建一个包装对象,也就是装饰来包裹真实的对象。(出自百度百科)

前些天学习了几个基本的设计模式(工厂模式,单例模式,建造者模式),后面以为就告一段落了,想着以后随着学习的深入慢慢学习可是没想到在补java基础的时候看到了IO流,里面的BufferedReader类其实就是一个装饰着模式(只需要关闭BufferedReader的流,而不需要关闭创建它时候参数对象的流)。然后我就把装饰着模式也顺带看了一下,发现这不就是之前学java多线程编程的时候常用的手法吗(先写一个Service类,里面含一个service功能方法,然后创建一个线程类里面包含一个Service引用,构造函数中传入Service实例,并在线程的run方法中调用service方法,最后在main方法中创建Service实例,并将Service实例传入)?
虽然线程类未对Service进行扩展(单纯在run方法中调用service),但是也是这种设计模式可不就是装饰着模式吗!

1.首先我们要知道为什么要使用装饰者模式,上面我们说到了装饰着模式不必改变原类文件和使用继承的情况下动态扩展一个对象的功能,为什么我们不用继承的方法呢?只要重写就能够对方法进行扩展,我们说过设计模式遵循几个目的,其中之一就是解耦,继承的关系就像是父子关系一样,亲不可分,装饰者模式则更像是朋友关系。
装饰着模式的要求:
①装饰着中含有被装饰者的引用
②装饰者和被装饰者实现同一个类型(不强制要求)

下面给出线程中使用到的装饰者模式

//被装饰者
public class Service {
    synchronized public static void printA() {

    }
//装饰者
public class ThreadA extends Thread {
    private Service service;
    public ThreadA(Service service) {
        super();
        this.service=service;
    }
    public void run() {
        service.printA();
    }
}

下面再来看看BufferedReader 的close方法的装饰者模式:

package Decorator;
//被装饰者
public class FileReader {
    public void close() {
        System.out.println("FileReader close");
    }
}
package Decorator;
//装饰者
public class BufferedReader {
    FileReader rd;
    public BufferedReader(FileReader rd){
        this.rd=rd;
    }

    public void close() {
        System.out.println("BufferedReader close");
        rd.close();
        System.out.println("BufferedReader close");
    }
}
package Decorator;
//Test方法
public class Test {
    public static void main(String[] args) {
        FileReader fr = new FileReader();
        BufferedReader br = new BufferedReader(fr);
        br.close();
    }
}
//输出:
//BufferedReader close
//FileReader close
//BufferedReader close

如果想要使得这个例子更像jdk中BufferedReader所实现的装饰者模式,我们应该再添加一个抽象类:Reader(BufferedReader和FileReader都要继承这个类),里面包含一个close抽象方法,再对以上代码做一定改动。

package Decorator;

public abstract class Reader {
    abstract void close();
}
//FileReader rd;
//  public BufferedReader(FileReader rd){
//      this.rd=rd;
//  }
Reader rd;
public BufferedReader(Reader rd){
        this.rd=rd;
    }
//需要将上面的注释代码改为下面的代码,还需要将BufferedReader和FileReader继承Reader

所以我们现在应该明白在用到转换流的时候

BufferedReader br = new BufferedReader(new InputStreamReader(new FileInputStream("F:/test")));

在装饰者类方法中会调用被装饰者的close方法,所以我们只需要关闭装饰者的流,而不需要再次关闭被装饰者的流。

以上就是是装饰者模式的一些简单分析理解。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值