简单Java代码实例助你通俗易懂的理解什么是装饰(者)设计模式 (Decorator)

版权声明:觉得此文有用的,不嫌麻烦的,就留个言呐,或者点个赞呐(额,就是文章底部的“顶”啦),要是嫌弃麻烦呢,也麻烦点个赞嘛,要是实在不想点赞呢,也不是不可以。 但是,你要是想踩一脚呢,那还是赶紧,马上,快快的闪人。 小心我手里三十米长的大刀。 哼哼。想想都怕 !!! https://blog.csdn.net/qq_27093465/article/details/53320859

首先抛开到处都有的文字概念。来看下面的例子。
现在以:人吃饭。这个需求为例。来讲解这个设计模式。
1.0:想当年,人们都比较朴实。吃饭就是简简单单的吃饭。
那么PersonBefore类里面一个简单的方法chifan();


2.0:现如今,人们生活水平高了。吃饭的花样也多了,简单的吃饭已经不能满足需求。
那么怎么修改原来的代码才合适呢。总不能分分钟推到重构吧。


先看下面代码实现:

PersonBefore类,最原始的需求实现。

package com.lxk.designPattern.decorator;

/**
 * 被装饰的类
 * (被增强对象)
 * <p>
 * Created by lxk on 2016/11/24
 */
public class PersonBefore {
    public void eat() {
        System.out.println("吃饭");
    }
}


PersonNow类,需求增强之后的实现类。

package com.lxk.designPattern.decorator;

/**
 * 装饰类
 * (要去增强目标对象的类)
 * 装饰类通常会通过构造方法接收被装饰的对象。
 * 并基于被装饰的对象的功能,提供更强的功能。
 * <p>
 * Created by lxk on 2016/11/24
 */
public class PersonNow {
    private PersonBefore p;

    PersonNow(PersonBefore p) {
        this.p = p;
    }

    public void superChifan() {
        //简单扩展
        System.out.println("开胃酒");
        p.eat();
        System.out.println("甜点");
        System.out.println("来一根烟");
    }
}

PersonDemo类,需求实际被调用的类。
package com.lxk.designPattern.decorator;

/**
 * 装饰设计模式:
 * 当想要对已有的对象进行功能增强时,
 * 可以定义类,将已有对象传入,基于已有的功能,并提供加强功能。
 * 那么自定义的该类称为装饰类。
 * <p>
 * 装饰类通常会通过构造方法接收被装饰的对象。
 * 并基于被装饰的对象的功能,提供更强的功能。
 */

class PersonDemo {
    public static void main(String[] args) {
        PersonBefore p = new PersonBefore();
        //p.eat();//这个是需求1.0
        PersonNow sp = new PersonNow(p);
        sp.superChifan();
    }
}

此代码只为简单易懂的理解这个装饰者设计模式。你可能会考虑到使用继承也可以实现类似效果,继承和装饰模式之间有什么差别呢?那是后话了。再说吧。
我还想问这个装饰者设计模式和代理模式的区别呢?和AOP的差别在哪?


下面是摘自某度文库的--装饰模式的概念的详细文字描述。真不是分分钟能明白说的都是啥。


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

装饰模式的特点
(1) 装饰对象和真实对象有相同的接口。这样客户端对象就能以和真实对象相同的方式和装饰对象交互。
(2) 装饰对象包含一个真实对象的引用(reference)
(3) 装饰对象接受所有来自客户端的请求。它把这些请求转发给真实的对象。
(4) 装饰对象可以在转发这些请求以前或以后增加一些附加功能。这样就确保了在运行时,不用修改给定对象的结构就可以在外部增加附加的功能。在面向对象的设计中,通常是通过继承来实现对给定类的功能扩展。

适用性
以下情况使用Decorator模式
1. 需要扩展一个类的功能,或给一个类添加附加职责。
2. 需要动态的给一个对象添加功能,这些功能可以再动态的撤销。
3. 需要增加由一些基本功能的排列组合而产生的非常大量的功能,从而使继承关系变的不现实。
4. 当不能采用生成子类的方法进行扩充时。一种情况是,可能有大量独立的扩展,为支持每一种组合将产生大量的子类,使得子类数目呈爆炸性增长。另一种情况可能是因为类定义被隐藏,或类定义不能用于生成子类。

优点
1. Decorator模式与继承关系的目的都是要扩展对象的功能,但是Decorator可以提供比继承更多的灵活性。
2. 通过使用不同的具体装饰类以及这些装饰类的排列组合,设计师可以创造出很多不同行为的组合。

缺点
1. 这种比继承更加灵活机动的特性,也同时意味着更加多的复杂性。
2. 装饰模式会导致设计中出现许多小类,如果过度使用,会使程序变得很复杂。
3. 装饰模式是针对抽象组件(Component)类型编程。但是,如果你要针对具体组件编程时,就应该重新思考你的应用架构,以及装饰者是否合适。当然也可以改变Component接口,增加新的公开的行为,实现“半透明”的装饰者模式。在实际项目中要做出最佳选择。


实际使用
java IO 流是典型的装饰模式。

这倒是真的,看前2篇 BufferedReader BufferedWriter 都是把字符读写流资源作为参数,传进类内部,对其进行功能增强。使得读写的效率得到提高。果然是实际使用此模式的好例子。






阅读更多
换一批

没有更多推荐了,返回首页