装饰者模式:动态地将责任附加到对象上。若要扩展功能,装饰者提供了比继承更有弹性的替代方案。(星巴兹咖啡)

设计原则:类应该对扩展开放,对修改关闭。

我们的目标是允许类容易扩展,在不修改现有代码的情况下,就可以搭配新的行为。如能实现这样的目标,有什么好处呢?这样的设计具有弹性可以应对改变,可以接受新的功能来应对改变的需求。

工程名称:Decorator(eclipse)  下载目录:http://www.cnblogs.com/jrsmith/admin/Files.aspx ,Decorator.zip

设计模式之三:装饰者模式(简单实现(星巴兹咖啡))

 1 package com.jyu.abstractclass;
 2 
 3 /**
 4  * 饮料(组件)
 5  * @author JRSmith
 6  *
 7  */
 8 public abstract class Beverage {
 9 
10     protected String description = "Unknown Beverage";
11     
12     /**getDescription()已经在此实现了,但是cost()必须在子类中实现*/
13     public String getDescription(){
14         return description;
15     }
16     
17     public abstract double cost();
18 }
 1 package com.jyu.abstractclass;
 2 
 3 /**
 4  * 调料
 5  * @author JRSmith
 6  *
 7  */
 8 public abstract class Condiment extends Beverage {
 9 
10     @Override
11     public abstract String getDescription();
12 }
View Code

 1 package com.jyu.extendsbeverage;
 2 
 3 import com.jyu.abstractclass.Beverage;
 4 
 5 /**
 6  * 低咖啡因
 7  * @author JRSmith
 8  *
 9  */
10 public class Decat extends Beverage {
11 
12     public Decat() {
13         description = "Decat Coffee";
14     }
15 
16     @Override
17     public double cost() {
18         return 1.05;
19     }
20 
21 }
View Code

 1 package com.jyu.extendsbeverage;
 2 
 3 import com.jyu.abstractclass.Beverage;
 4 
 5 /**
 6  * 深焙
 7  * @author JRSmith
 8  *
 9  */
10 public class DarkRoast extends Beverage {
11 
12     public DarkRoast() {
13         description = "DarkRoast Coffee";
14     }
15 
16     @Override
17     public double cost() {
18         return .99;
19     }
20 
21 }
View Code

 1 package com.jyu.extendsbeverage;
 2 
 3 import com.jyu.abstractclass.Beverage;
 4 
 5 /**
 6  * 浓缩咖啡
 7  * @author JRSmith
 8  *
 9  */
10 public class Espresso extends Beverage {
11 
12     public Espresso(){
13         description = "Espresso Coffee";
14     }
15     
16     @Override
17     public double cost() {
18         return 1.99;
19     }
20 
21 }
View Code

 1 package com.jyu.extendsbeverage;
 2 
 3 import com.jyu.abstractclass.Beverage;
 4 
 5 /**
 6  * 综合咖啡
 7  * @author JRSmith
 8  *
 9  */
10 public class HouseBlend extends Beverage {
11 
12     public HouseBlend() {
13         description = "House Blend Coffee";
14     }
15 
16     @Override
17     public double cost() {
18         return .89;
19     }
20 
21 }
View Code

 1 package com.jyu.extendscondiment;
 2 
 3 import com.jyu.abstractclass.Beverage;
 4 import com.jyu.abstractclass.Condiment;
 5 
 6 /**
 7  * 摩卡
 8  * @author JRSmith
 9  *
10  */
11 public class Mocha extends Condiment {
12 
13     protected Beverage beverage;
14     
15     public Mocha(Beverage beverage) {
16         this.beverage = beverage;
17     }
18 
19     @Override
20     public String getDescription() {
21         return this.beverage.getDescription() + " , Mocha";
22     }
23 
24     @Override
25     public double cost(){
26         return 0.20 + this.beverage.cost();
27     }
28 
29 }
View Code

 1 package com.jyu.extendscondiment;
 2 
 3 import com.jyu.abstractclass.Beverage;
 4 import com.jyu.abstractclass.Condiment;
 5 
 6 /**
 7  * 豆浆
 8  * @author JRSmith
 9  *
10  */
11 public class Soy extends Condiment {
12 
13     protected Beverage beverage;
14     
15     public Soy(Beverage beverage) {
16         this.beverage = beverage;
17     }
18 
19     @Override
20     public String getDescription() {
21         return this.beverage.getDescription() + " , Soy";
22     }
23 
24     @Override
25     public double cost() {
26         return 0.15 + this.beverage.cost();
27     }
28 
29 }
View Code

 1 package com.jyu.extendscondiment;
 2 
 3 import com.jyu.abstractclass.Beverage;
 4 import com.jyu.abstractclass.Condiment;
 5 
 6 /**
 7  * 奶泡
 8  * @author JRSmith
 9  *
10  */
11 public class Whip extends Condiment {
12 
13     protected Beverage beverage;
14     
15     public Whip(Beverage beverage) {
16         this.beverage = beverage;
17     }
18 
19     @Override
20     public String getDescription() {
21         return this.beverage.getDescription() + " , Whip";
22     }
23 
24     @Override
25     public double cost() {
26         return 0.10 + this.beverage.cost();
27     }
28 
29 }
 1 package com.jyu.test;
 2 
 3 import com.jyu.abstractclass.Beverage;
 4 import com.jyu.extendsbeverage.DarkRoast;
 5 import com.jyu.extendsbeverage.Espresso;
 6 import com.jyu.extendsbeverage.HouseBlend;
 7 import com.jyu.extendscondiment.Mocha;
 8 import com.jyu.extendscondiment.Soy;
 9 import com.jyu.extendscondiment.Whip;
10 
11 public class StarbuzzCoffee {
12 
13     /**
14      * @param args
15      */
16     public static void main(String[] args) {
17         
18         /**订一杯Espresso,不需要调料,打印出它的描述与价钱*/
19         Beverage beverage = new Espresso();
20         System.out.println(beverage.getDescription() + " $" + beverage.cost());
21         
22         /**制造出一个DarkRoast对象。用Mocha装饰它,用第二个Mocha装饰它,用Whip装饰它*/
23         Beverage beverage2 = new DarkRoast();
24         beverage2 = new Mocha(beverage2);
25         beverage2 = new Mocha(beverage2);
26         System.out.println(beverage2.getDescription() + " $" + beverage2.cost());
27         
28         /**最后,再来一杯调料为豆浆、摩卡、奶泡的HouseBlend咖啡*/
29         Beverage beverage3 = new HouseBlend();
30         beverage3 = new Soy(beverage3);
31         beverage3 = new Mocha(beverage3);
32         beverage3 = new Whip(beverage3);
33         System.out.println(beverage3.getDescription() + " $" + beverage3.cost());
34         
35         
36     }
37 
38 }