23种设计模式-装饰器模式

1.产生背景

  • 为什么需要装饰器模式

某些情况,当一个类已经存在,并且可以对外提供核心功能时,但是,某个时刻,希望对这个类进行功能增强(如:增加缓存);通常情况,我们可以修改原来的类,并增加对应的增强功能即可;

但是,这种方式违背了“开-闭”原则,需要修改原来的代码;而且不够灵活,如果有某个时刻又不想使用缓存,又需要修改原来的代码,显然,这不是一个很好的解决方案;

2.概念

装饰器模式(Decorator Pattern)允许向一个现有的对象添加新的功能,同时又不改变其结构。

本质: 引入一个中介类,这个类实现了被装饰者相同的接口,对外假装成被装饰者,并通过引用被装饰者,在调用被装饰者前后做一些附加功能(如:缓存,参数预处理);

3.目的

不修改原来代码的情况下,动态地给一个对象添加一些额外的职责和功能

本质:动态增加功能;把需要新增加的功能预先制作成零件,在需要时“动态“的添加到对象上;

装饰器模式相比生成子类更为灵活

4.解决方案

本质:引入一个第三方中介类,这个类实现了被装饰类的接口,并引用了被装饰对象,对外假装成被装饰对象,对内通过调用被装饰对象完成最终功能,在调用被装饰对象之前之后,可以做一些额外的功能(这也是装饰模式功能增强的地方);

  • 引入中介对象
  • 中介对象实现被装饰类的接口(对外假装成被装饰类)
  • 中介对象内部引用被装饰类(并把真实功能委托给被装饰对象);
  • 中介对象在调用被装饰对象前后:增加特殊功能

5. 类图

这里写图片描述

6.优缺点

优点:

  • 松耦合
    在不修改原来代码的情况下,动态的为原类增加新功能

  • 扩展性高
    只需要增加新的装饰类,就可以对原类不断增加新功能

  • 灵活
    不需要通过继承来扩展,而且可以动态增加或去除新装饰类,从而随意对原对象增加或减少某些功能

最核心的目的:在不修改原代码的情况下,动态的为对象增加或减少某些功能

缺点:

  • 额外引入第三方

7.应用场景

  • 扩展类的功能时
  • 动态增加或取消某些功能时

“与代理模式的区别”
在学习装饰器模式时,会发现它与代理模式无论从实现结构,还是功能目的都非常接近;

装饰器模式侧重的是对功能的增强,不改变原功能;
装饰器模式使用方明确知道自己需要什么的增强功能,硬编码使用;

代理模式侧重于对原功能的改变(特别是访问权限的控制)
代理模式分为静态和动态代理,动态代理是在调用方不知情的情况下使用;

如果代理模式使用静态代理实现,而且也是侧重对功能的增强,那么他们之间没有任何区别(如:spring中通过动态代理实现缓存或日志)

因此:代理在java中,更多的应用在动态AOP上;

8.现实案例

JDK中的流处理;
ByteArrayInputStream
FileInputStream
ObjectInputStream
PipedInputStream

9. 注意事项

猜你喜欢

转载自blog.csdn.net/yangspgao/article/details/80556842
今日推荐