装饰者模式(Decorator Pattern)是指在不改变原有对象的基础之上,将功能附加到对 象上,提供了比继承更有弹性的替代方案(扩展原有对象的功能),属于结构型模式。 装饰者模式在我们生活中应用也比较多如给煎饼加鸡蛋;给蛋糕加上一些水果;给房子 装修等,为对象扩展一些额外的职责。装饰者在代码程序中适用于以下场景
1、用于扩展一个类的功能或给一个类添加附加职责。
2、动态的给一个对象添加功能,这些功能可以再动态的撤销。
有很多小伙伴爱喝奶茶,奶茶也有很多种口味,比如椰肉、珍珠、红豆等,我们就奶茶的这个场景来实践一把装饰者模式。
奶茶抽象类 AbstractMilkyTea
public abstract class AbstractMilkyTea {
protected abstract String getInfo();
protected abstract double getPrice();
}
奶茶的基础套餐 BaseMilkyTea
public class BaseMilkyTea extends AbstractMilkyTea {
protected String getInfo() {
return "奶茶";
}
protected double getPrice() {
return 10;
}
}
抽象装饰者 AbstractDecorator
public abstract class AbstractDecorator extends AbstractMilkyTea {
private AbstractMilkyTea baseMilkyTea;
public AbstractDecorator(AbstractMilkyTea baseMilkyTea) {
this.baseMilkyTea = baseMilkyTea;
}
@Override
protected String getInfo() {
return baseMilkyTea.getInfo();
}
@Override
protected double getPrice() {
return baseMilkyTea.getPrice();
}
}
椰肉装饰者 CocoDecorator
public class CocoDecorator extends AbstractDecorator {
public CocoDecorator(AbstractMilkyTea baseMilkyTea) {
super(baseMilkyTea);
}
protected String getInfo() {
return super.getInfo() + "椰肉";
}
protected double getPrice() {
return super.getPrice() + 3;
}
}
珍珠装饰者 PearlDecorator
public class PearlDecorator extends AbstractDecorator {
public PearlDecorator(AbstractMilkyTea baseMilkyTea) {
super(baseMilkyTea);
}
@Override
protected String getInfo() {
return super.getInfo() + "珍珠";
}
@Override
protected double getPrice() {
return super.getPrice() + 2;
}
}
红豆装饰者 RedBeanDecorator
public class RedBeanDecorator extends AbstractDecorator {
public RedBeanDecorator(AbstractMilkyTea baseMilkyTea) {
super(baseMilkyTea);
}
protected String getInfo() {
return super.getInfo()+"红豆";
}
protected double getPrice() {
return super.getPrice()+1;
}
}
测试类
public class MilkyTeaTest {
public static void main(String[] args) {
AbstractMilkyTea baseMilkyTea = new BaseMilkyTea();
baseMilkyTea = new PearlDecorator(baseMilkyTea);
baseMilkyTea = new RedBeanDecorator(baseMilkyTea);
System.out.println(baseMilkyTea.getPrice());
System.out.println(baseMilkyTea.getInfo());
}
}