简介
装饰者模式又称包装模式,是指不改变原有对象的基础上,将功能附加到对象上,提供了比继承更有弹性的替代方案.属于结构型设计模式
案例描述及实现
案例描述
咖啡厅售卖咖啡并且可以添加材料,咖啡包括Decaf和ShortBlack两种,材料包括salt和sugar两种。每种咖啡和材料都有各自的描述和价格。顾客在购买咖啡时可以选择一种咖啡并选择添加一个或多种材料。如果按照排列组合的方式去计算每种可能的情况,那么会使得代码非常复杂。因此需要一种全新的模式去解决以上问题。
实现
通过材料对咖啡进行装饰,以实现代码的简便实现。首先构造咖啡的基类饮品类。
public abstract class Drink {
private 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; }
//计算当前这杯drink多少钱
public abstract float cost();
}
在基类的基础上构造咖啡类
public class Coffee extends Drink {
@Override
public float cost() { return getPrice(); }
}
在咖啡类的基础上构造Decaf和ShortBlack两类咖啡
public class Decaf extends Coffee {
public Decaf(){
setDes("Decaf");
setPrice(10f);
}
}
public class ShortBlack extends Coffee {
public ShortBlack(){
setDes("ShortBlack");
setPrice(5f);
}
}
要实现材料对咖啡的装饰,需要装饰类的基类也继承咖啡的基类饮品类(因为材料也有价格和描述,此处是为了方便所以直接将饮品的材料和价格继承)。其中必须将饮品组合在里边,方便计算总价格。
public class Decorator extends Drink {
private Drink drink;
@Override
public float cost() {
return drink.cost()+this.getPrice();
}
public Decorator(Drink drink){ this.drink=drink; }
@Override
public String getDes() { return super.getDes()+" "+super.getPrice()+" && "+drink.getDes(); }
}
在装饰类基类的基础上分别实现salt类和sugar类
public class Salt extends Decorator {
public Salt(Drink drink) {
super(drink);
setDes("salt");
setPrice(1);
}
}
public class Sugar extends Decorator {
public Sugar(Drink drink) {
super(drink);
setDes("糖");
setPrice(2);
}
}
模拟咖啡厅售卖咖啡的流程,比如顾客要一杯加了salt和sugar的ShortBlack。那么通过代码实现如下,可以很方便的实现装饰的功能,减少了代码的冗余度。
public static void main(String[] args) {
Drink order = new ShortBlack();
System.out.println(order.getDes());
System.out.println(order.cost());
System.out.println("===============");
//加sugar
order = new Sugar(order);
System.out.println(order.getDes());
System.out.println(order.cost());
System.out.println("===============");
//加salt
order = new Salt(order);
System.out.println(order.getDes());
System.out.println(order.cost());
}
JAVA中的装饰者模式实现
Java中的IO使用到了装饰者模式。其中InputStream是抽象类,类似上述案例的Drink。FileInputStream是InputStream的子类,类似于上述案例的Decaf和ShortBlack。FilterInputStream是InputStream的子类,类似于上述案例的Decorator,其中组合了InputStream,即被装饰者。而DataInputSream是FilterInputStream的子类,具体的修饰者,相当于上述的salt和sugar。
版权声明:本文为NWU_LK原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接和本声明。