设计模式 - 装饰者模式
1. 定义:动态的将责任附加到对象上。若要扩展功能,装饰者提供了比继承更有弹性的替代方案。
2. 类结构图:
3. 代码实现
1 package com.dcz.decorate; 2 3 /** 4 * 饮料 抽象类 5 * @author Administrator 6 */ 7 8 public abstract class Beverage { 9 10 // 描述 11 String description = "Unknown Beverage"; 12 13 // 获取饮料描述 14 public String getDescription(){ 15 return this.description; 16 } 17 18 // 计算价格方法 19 public abstract double cost(); 20 21 }
1 package com.dcz.decorate; 2 3 /** 4 * 综合 - 咖啡 5 * @author Administrator 6 * 7 */ 8 9 public class HouseBlend extends Beverage { 10 11 public HouseBlend(){ 12 description = "House Blend Coffee"; 13 } 14 15 @Override 16 public double cost() { 17 return 0.89; 18 } 19 20 }
1 package com.dcz.decorate; 2 3 /** 4 * 深陪 - 咖啡 5 * @author Administrator 6 * 7 */ 8 9 public class DarkRoast extends Beverage { 10 11 public DarkRoast(){ 12 description = "Dark Roast Coffee"; 13 } 14 15 @Override 16 public double cost() { 17 return 0.99; 18 } 19 20 }
1 package com.dcz.decorate; 2 3 /** 4 * 超浓缩 - 咖啡 5 * @author Administrator 6 */ 7 8 public class Espresso extends Beverage { 9 10 public Espresso(){ 11 description = "Espresso Coffee"; 12 } 13 14 @Override 15 public double cost() { 16 return 1.99; 17 } 18 19 }
1 package com.dcz.decorate; 2 3 /** 4 * 浓缩 - 咖啡 5 * @author Administrator 6 * 7 */ 8 9 public class Decat extends Beverage { 10 11 public Decat(){ 12 description = "Decat Coffee"; 13 } 14 15 @Override 16 public double cost() { 17 return 1.99; 18 } 19 20 }
//-----------------------------------------------------------------------
1 package com.dcz.decorate; 2 3 /** 4 * 调味品 - 装饰者 5 * @author Administrator 6 * 7 */ 8 9 public abstract class CondimentDecorator extends Beverage { 10 11 // 所有的饮料装饰着必须重新实现此方法 12 public abstract String getDescription(); 13 14 }
1 package com.dcz.decorate; 2 3 /** 4 * 摩卡- 配料 5 * @author Administrator 6 * 7 */ 8 9 public class Mocha extends CondimentDecorator { 10 11 // 用一个实例变量记录饮料,也就是被装饰者 12 Beverage beverage; 13 14 public Mocha(Beverage beverage){ 15 this.beverage = beverage; 16 } 17 18 @Override 19 public String getDescription() { 20 return beverage.getDescription() + ", Mocha"; 21 } 22 23 // 计算摩卡价格 24 public double cost(){ 25 return 0.20 + beverage.cost(); 26 } 27 28 29 }
1 package com.dcz.decorate; 2 3 /** 4 * 豆浆 - 配料 5 * @author Administrator 6 * 7 */ 8 9 public class Soy extends CondimentDecorator { 10 11 // 记录饮料被装饰者 12 Beverage beverage; 13 14 public Soy(Beverage beverage){ 15 this.beverage = beverage; 16 } 17 18 @Override 19 public String getDescription() { 20 return beverage.getDescription() + ", Soy"; 21 } 22 23 public double cost(){ 24 return 0.15 + beverage.cost(); 25 } 26 27 }
1 package com.dcz.decorate; 2 3 /** 4 * 奶泡 - 配料 5 * @author Administrator 6 * 7 */ 8 9 public class Whip extends CondimentDecorator { 10 11 Beverage beverage; 12 13 public Whip(Beverage beverage){ 14 this.beverage = beverage; 15 } 16 17 @Override 18 public String getDescription() { 19 return beverage.getDescription() + ", Ship"; 20 } 21 22 // 计算奶泡价格 23 public double cost(){ 24 return 0.10 + beverage.cost(); 25 } 26 27 }
// ----------------------------------------------------------------------------------------以下是测试类
1 package com.dcz.decorate; 2 3 public class TestStrbuzzCoffee { 4 5 public static void main(String[] args) { 6 7 // 要一杯超浓缩咖啡 8 Beverage espresso = new Espresso(); 9 System.out.println(espresso.getDescription() + ", $:" + espresso.cost()); 10 11 // 要一杯深陪咖啡,双倍摩卡加奶泡 12 Beverage darkRoast = new DarkRoast(); 13 // 使用第一个摩卡装饰 14 darkRoast = new Mocha(darkRoast); 15 // 使用第二个摩卡装饰 16 darkRoast = new Mocha(darkRoast); 17 // 使用奶泡装饰 18 darkRoast = new Whip(darkRoast); 19 System.out.println(darkRoast.getDescription() + ", $:" + darkRoast.cost()); 20 21 // 最后要在一杯调料为豆浆,摩卡,奶泡的综合咖啡 22 Beverage HouseBlend = new HouseBlend(); 23 // 使用豆浆装饰 24 HouseBlend = new Soy(HouseBlend); 25 // 使用摩卡装饰 26 HouseBlend = new Mocha(HouseBlend); 27 // 使用奶泡装饰 28 HouseBlend = new Whip(HouseBlend); 29 System.out.println(HouseBlend.getDescription() + ", $:" + HouseBlend.cost()); 30 31 } 32 33 }