学习设计模式的日常Demo
装饰者模式介绍
- 结构型模式
- 范围\目的:对象模式
装饰者模式原理
装饰模式就是给一个对象增加一些新的功能,而且是动态的,要求装饰对象和被装饰对象实现同一个接口,装饰对象持有被装饰对象的实例
装饰者模式案例
代码实现:
被装饰物
// 定义抽象的饮品类
public abstract class Drink {
public String des; // 描述
private float price = 0.0f; // 价格
public String getDes() {
return des;
}
public void setDes(String des) {
this.des = des;
}
public float getPrice() {
return price;
}
public void setPrice(float price) {
this.price = price;
}
// 计算费用的抽象方法
// 子类来实现
public abstract float cost();
}
// 定义继承了抽象饮品类的主类咖啡类
public class Coffee extends Drink{
@Override
public float cost() {
return super.getPrice();
}
}
// 定义三种继承了主类咖啡类的具体咖啡
public class ACoffee extends Coffee {
public ACoffee() {
setDes("A种咖啡");
setPrice(28.0f);
}
}
public class BCoffee extends Coffee {
public BCoffee() {
setDes("B种咖啡");
setPrice(25.0f);
}
}
public class DCoffee extends Coffee {
public DCoffee() {
setDes("D种咖啡");
setPrice(20.0f);
}
}
装饰者
// 定义主类装饰类,继承了抽象饮品类,并将其聚合在类中
public class Decorator extends Drink {
// 被装饰者
private Drink drink;
public Decorator(Drink drink) {
this.drink = drink;
}
@Override
public float cost() {
// 小料价格加上单品咖啡价格
return super.getPrice() + drink.cost();
}
@Override
public String getDes() {
return super.des + " " + super.getPrice() + " && " + drink.getDes();
}
}
// 定义继承了主类装饰类的两种装饰品
// 具体的装饰物
public class Chocolate extends Decorator {
public Chocolate(Drink drink) {
super(drink);
setDes("一份巧克力");
setPrice(5.0f);
}
}
public class Milk extends Decorator {
public Milk(Drink drink) {
super(drink);
setDes("一份牛奶");
setPrice(2.0f);
}
}
// 测试类
public class Test {
public static void main(String args[]) {
// 创建一份A类咖啡单品(未加小料(未被装饰))
Drink a = new ACoffee();
System.out.println("描述:" + a.getDes());
System.out.println("咖啡单价:" + a.getPrice());
System.out.println("-----------------------");
// 两份巧克力,一份牛奶装饰A咖啡
// 开始加入小料
a = new Milk(a);
System.out.println("描述:" + a.getDes());
System.out.println("总费用:" + a.cost());
System.out.println("-----------------------");
a = new Chocolate(a);
System.out.println("描述:" + a.getDes());
System.out.println("总费用:" + a.cost());
System.out.println("-----------------------");
a = new Chocolate(a);
System.out.println("描述:" + a.getDes());
System.out.println("总费用:" + a.cost());
System.out.println("-----------------------");
}
}
装饰者模式在JDK中的应用
装饰者模式注意事项和细节说明
优点:动态地为对象增加新的功能或者撤销功能(继承就不能做到这一点)
缺点:会产生过多的相似的对象,不容易排错!