结构型-装饰器模式
# 什么是装饰器模式?
- 装饰器类和原始类继承同样的父类,这样我们可以对原始类“嵌套”多个装饰器类。
- 装饰器类是对功能的增强,这也是装饰器模式应用场景的一个重要特点。
# 为什么用装饰器模式?
- 装饰器模式主要解决继承关系过于复杂的问题,通过组合来替代继承。
- 它主要的作用是给原始类添加增强功能。这也是判断是否该用装饰器模式的一个重要的依据。
- 可以对原始类嵌套使用多个装饰器。为了满足这个应用场景,在设计的时候,装饰器类需要跟原始类继承相同的抽象类或者接口。
# 如何使用装饰器模式?
public interface BakeryComponent {
public String getName();
public double getPrice();
}
@Data
public class CakeBase implements BakeryComponent {
private String name = "Cake Base";
private double price = 200.0;
@Override
public String getName() {
return this.name;
}
@Override
public double getPrice() {
return this.price;
}
}
@Data
public class PastryBase implements BakeryComponent {
private String name = "Pastry Base";
private double price = 200.0;
@Override
public String getName() {
return this.name;
}
@Override
public double getPrice() {
return this.price;
}
}
public abstract class Decorator implements BakeryComponent {
private BakeryComponent bakeryComponent = null;
protected String name = "Undefined Decorator";
protected double price = 0.0;
public Decorator(BakeryComponent bakeryComponent) {
this.bakeryComponent = bakeryComponent;
}
@Override
public String getName() {
return this.bakeryComponent.getName() + ", " + this.name;
}
@Override
public double getPrice() {
return this.price + this.bakeryComponent.getPrice();
}
}
public class ArtificialScentDecorator extends Decorator {
public ArtificialScentDecorator(BakeryComponent bakeryComponent) {
super(bakeryComponent);
this.name = "ArtificialScent";
this.price = 3.0;
}
}
public class CherryDecorator extends Decorator {
public CherryDecorator(BakeryComponent bakeryComponent) {
super(bakeryComponent);
this.name = "Cherry";
this.price = 2.0;
}
}
public class CreamDecorator extends Decorator {
public CreamDecorator(BakeryComponent bakeryComponent) {
super(bakeryComponent);
this.name = "Cream";
this.price = 1.0;
}
}
public class NameCardDecorator extends Decorator {
public NameCardDecorator(BakeryComponent bakeryComponent) {
super(bakeryComponent);
this.name = "NameCard";
this.price = 4.0;
}
}
public class App {
private static void printProductDetails(BakeryComponent bakeryComponent) {
String out = "Item: " + bakeryComponent.getName() + ", Price: " + bakeryComponent.getPrice();
System.out.println(out);
}
public static void main(String[] args) {
System.out.println("Hello World!");
CakeBase cakeBase = new CakeBase();
printProductDetails(cakeBase);
CreamDecorator creamDecorator = new CreamDecorator(cakeBase);
printProductDetails(creamDecorator);
CherryDecorator cherryDecorator = new CherryDecorator(creamDecorator);
printProductDetails(cherryDecorator);
ArtificialScentDecorator artificialScentDecorator = new ArtificialScentDecorator(cherryDecorator);
printProductDetails(artificialScentDecorator);
NameCardDecorator nameCardDecorator = new NameCardDecorator(artificialScentDecorator);
printProductDetails(nameCardDecorator);
PastryBase pastry = new PastryBase();
printProductDetails(pastry);
CreamDecorator creamDecorator1 = new CreamDecorator(pastry);
printProductDetails(creamDecorator1);
}
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
# 装饰器模式使用场景
- Java 中的 I/O 类库符合这一特征
上次更新: 2020/09/08, 15:09:00