设计模式的应用场景(9)--装饰模式

装饰模式

定义:装饰模式以对客户端透明的方式扩展对象的功能,是继承方案的一个替代方案,提供比继承更多的灵活性。

优点:能够提供比使用继承关系更加灵活的拓展对象的功能,它可以动态增加对象的功能并且可以随意组合这些功能。

缺点:使用装饰模式进行设计往往会产生很多看上去相似的小对象。

使用时机:当系统需要扩展一个类的功能,或者客户端需要动态的给一个对象添加功能,并且使用继承会很复杂时候。

其实对于装饰者模式大家并不陌生,相反接触的还很平凡,因为Java中的IO机制就用到了装饰者模式。比如大家最常用的语句:

BufferedReader br = new BufferedReader(new InputStreamReader(new FileInputStream(filepath)));

BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(System.out));

就是最常见的装饰者模式了,通过BufferedReader对已有对象FileReader的功能进行加强和优化。其实它不仅可以加强FileReader,所有的字符输入流都可以通过这种方式进行包装。它是如何实现的呢?注意重点来了:其实很简单,它只不过将所有的字符输入流抽象出了一个基类或接口 即Reader,然后通过构造方法的形式将Reader传递给BufferedReader,此时BufferedReader就可以对所有的字符输入流进行拦截和优化了。

  试想一下,如果采用继承机制,每个XXXReader就要衍生出一个BufferedXXXReader,再加上字符输出流和字节输入输出流,那么Java的IO体系结构该是多么的臃肿不堪啊!而装饰者模式的出现解决了这个问题,并且,装饰者的出现也再一次的证明了面向对象的设计原则:多用组合,少用继承!对扩展开放,对修改关闭!

下面再给出一个例子, 
小巩需要为公司设计手机相关的业务,

public interface Phone {
    void call(String name);
}
public class PhoneImpl implements Phone {
    public void call(String name) {
        System.out.println(name + " 正在通话中");
    }
}

彩铃手机

public class ColorPhoneDecorator extends PhoneDecorator {
    public ColorPhoneDecorator(Phone phone) {
        super(phone);
    }

    public void call(String name) {
        System.out.println("播放彩铃");
        super.call(name);
    }
}

广告手机

public class AdPhoneDecorator extends PhoneDecorator {
    public AdPhoneDecorator(Phone phone) {
        super(phone);
    }

    public void call(String name) {
        super.call(name);
        System.out.println("播放广告");
    }
}

假如客户需要支持彩铃和广告的手机

public class Client {
    public static void main(String[] argv) {
        Phone phone = new PhoneImpl();
        //如果需要彩铃的手机
        PhoneDecorator phoneDecorator = new ColorPhoneDecorator(phone);
    //  phoneDecorator.call("张三");
         //如果需要广告的手机
        //phoneDecorator = new AdPhoneDecorator(phone);
        //phoneDecorator.call("张三");
        //如果需要既播放彩铃又播放广告的手机
        phoneDecorator = new AdPhoneDecorator(phoneDecorator);
        phoneDecorator.call("张三");
    }
}

https://blog.csdn.net/zhi_fu/article/details/77677251

猜你喜欢

转载自blog.csdn.net/varyall/article/details/82735074
今日推荐