DecoratorMode
java 装饰器模式
结构
模式结构
- Component抽象构件角色:真实对象和装饰对象有相同的接口。这样,客户端对象就能够以与真实对象相同的方式同装饰对象交互。
- ConcreteCompoent具体构建角色(真实对象):定义一个将要接收附加责任的类。
- Decorator装饰角色:持有一个抽象构件的引用。装饰对象接受所有客户端的请求,并把这些请求转发给真实的对象。这样,就能在真实对象调用前后增加新的功能。
- ConcreteDecorate具体装饰角色:负责给构件对象增加新的功能。
代码结构:

代码
Person.java
Component抽象构件角色:
就是一个功能接口
1 | package com.user; |
Man.java
ConcreteCompoent具体构建角色(真实对象):
定义具体要被装饰的类(Man),这个类要实现上述接口(实现eat)
1 | package com.user; |
Decorator.java
Decorator装饰角色:
持有一个抽象构件的引用。装饰对象接受所有客户端的请求,并把这些请求转发给真实的对象。这样,就能在真实对象调用前后增加新的功能。
1 | package com.user; |
这个装饰器持有抽象接口(Person)的对象,并通过构造函数对它初始化,抽象装饰器也要实现步骤1中的抽象接口(Person),只不过抽象装饰器的实现方式比较特殊,它通过调用持有的抽象接口(Person)的对象的方法来实现抽象接口的功能函数。
那么算是一个接口的对象呢? 具体来说就是实现了这个接口的所有类,都可以实例化出一个对象来作为接口的对象,比如 Man me = new Man(); 因为Man 实现了 Person接口所以me 就是一个接口(Person)对象,所以把me 传递到具体装饰角色DecoratorA(Person person)的构造函数里不会报错。
DecoratorA.java
ConcreteDecorate具体装饰角色:
负责给构件对象增加新的功能。
1 | package com.user; |
DecoratorB.java
ConcreteDecorate具体装饰角色:
负责给构件对象增加新的功能。
1 | package com.user; |
总结
装饰器步骤:
- 定义要被装饰的功能(eat)抽象接口(Person)
- 定义具体要被装饰的类(Man),这个类要实现上述接口(实现eat)
- 定义抽象装饰器(Decorator),这个装饰器持有步骤1中的抽象接口(Person)的对象,并通过构造函数对它初始化,抽象装饰器也要实现步骤1中的抽象接口(Person),只不过 抽象装饰器的实现方式比较特殊,它通过调用持有的抽象接口(Person)的对象的方法来实现抽象接口的功能函数。 什么算是一个接口的对象呢? 具体来说就是实现了这个接口的所有类,都可以实例化出一个对象来作为接口的对象,比如 Man me = new Man(); 因为Man 实现了 Person接口 所以me 就是一个接口(Person)对象,所以把me 传递到DecoratorA(Person person)的构造函数里不会报错~
- 定义具体装饰器(DecoratorA/B/C…),包装功能函数eat,在super的基础上添加新功能。
优缺点
优点
- 为类添加新的功能 但是 Man这个类却不用改变,也不会产生新的继承类,类的数目会比较少
- 可以对一个对象进行多次装饰,创造出不同的表现
缺点
- 产生一堆装饰器对象 比如这里的DecoratorA da、DecoratorB db稍微占用内存空间
- 装饰模式易出错,调试排查比较麻烦。
感谢您的阅读,本文由
Space-X
版权所有。如若转载,请注明出处:Space-X(https://spaces-x.github.io/2019/03/31/DecoratorMode/)
