.NET设计模式(4):建造者模式(Builder Pattern)
2005-12-19 09:32:00
版权声明:原创作品,允许转载,转载时请务必以超链接形式标明文章 原始出处 、作者信息和本声明。否则将追究法律责任。http://terrylee.blog.51cto.com/342737/67747 |
建造者模式(Builder Pattern)
——.NET设计模式系列之四
Terrylee,2005年12月17日
概述
在软件系统中,有时候面临着“一个复杂对象”的创建工作,其通常由各个部分的子对象用一定的算法构成;由于需求的变化,这个复杂对象的各个部分经常面临着剧烈的变化,但是将它们组合在一起的算法确相对稳定。如何应对这种变化?如何提供一种“封装机制”来隔离出“复杂对象的各个部分”的变化,从而保持系统中的“稳定构建算法”不随着需求改变而改变?这就是要说的建造者模式。
本文通过现实生活中的买KFC的例子,用图解的方式来诠释建造者模式。
意图
将一个复杂的构建与其表示相分离,使得同样的构建过程可以创建不同的表示。
模型图
生活中的例子生成器模式将复杂对象的构建与对象的表现分离开来,这样使得同样的构建过程可以创建出不同的表现。这种模式用于快餐店制作儿童餐。典型的儿童餐包括一个主食,一个辅食,一杯饮料和一个玩具(例如汉堡、炸鸡、可乐和玩具车)。这些在不同的儿童餐中可以是不同的,但是组合成儿童餐的过程是相同的。无论顾客点的是汉堡,三名治还是鸡肉,过程都是一样的。柜台的员工直接把主食,辅食和玩具放在一起。这些是放在一个袋子中的。饮料被倒入杯中,放在袋子外边。这些过程在相互竞争的餐馆中是同样的。
实现过程图解在这里我们还是以去KFC店买套餐为例子,示意图如下:
客户端:顾客。想去买一套套餐(这里面包括汉堡,可乐,薯条),可以有1号和2号两种套餐供顾客选择。指导者角色:收银员。知道顾客想要买什么样的套餐,并告诉餐馆员工去准备套餐。
建造者角色:餐馆员工。按照收银员的要求去准备具体的套餐,分别放入汉堡,可乐,薯条等。
产品角色:最后的套餐,所有的东西放在同一个盘子里面。
下面开始我们的买套餐过程。
1.客户创建Derector对象,并用它所想要的Builder对象进行配置。顾客进入KFC店要买套餐,先找到一个收银员,相当于创建了一个指导者对象。这位收银员给出两种套餐供顾客选择:1普通套餐,2黄金套餐。完成的工作如时序图中红色部分所示。
程序实现: 1 using System;2 using System.Configuration;3 using System.Reflection;4 ![]() 5 namespace KFC6 {7 /// <summary>8 /// Client 类9 /// </summary>10 public class Client11 {12 public static void Main(string[] args)13 {14 FoodManager foodmanager = new FoodManager();15 ![]() 16 Builder instance;17 ![]() 18 Console.WriteLine("Please Enter Food No:");19 ![]() 20 string No = Console.ReadLine();21 ![]() 22 string foodType = ConfigurationSettings.AppSettings["No"+No];23 ![]() 24 instance = (Builder)Assembly.Load("KFC").CreateInstance("KFC." + foodType);25 ![]() 26 foodmanager.Construct(instance);27 }28 }29 }30 ![]() 产品(套餐)类:
1
using System;2 using System.Collections;3 ![]() 4 namespace KFC5 {6 /// <summary>7 /// Food类,即产品类8 /// </summary>9 public class Food10 {11 Hashtable food = new Hashtable();12 13 /// <summary>14 /// 添加食品15 /// </summary>16 /// <param name="strName">食品名称</param>17 /// <param name="Price">价格</param>18 public void Add(string strName,string Price)19 {20 food.Add(strName,Price);21 }22 23 /// <summary>24 /// 显示食品清单25 /// </summary>26 public void Show()27 {28 IDictionaryEnumerator myEnumerator = food.GetEnumerator();29 Console.WriteLine("Food List:");30 Console.WriteLine("------------------------------");31 string strfoodlist = "";32 while(myEnumerator.MoveNext())33 {34 strfoodlist = strfoodlist + "\n\n" + myEnumerator.Key.ToString();35 strfoodlist = strfoodlist + ":\t" +myEnumerator.Value.ToString();36 }37 Console.WriteLine(strfoodlist);38 Console.WriteLine("\n------------------------------");39 }40 }41 }42 ![]() 2.指导者通知建造器。收银员(指导者)告知餐馆员工准备套餐。这里我们准备套餐的顺序是:放入汉堡,可乐倒入杯中,薯条放入盒中,并把这些东西都放在盘子上。这个过程对于普通套餐和黄金套餐来说都是一样的,不同的是它们的汉堡,可乐,薯条价格不同而已。如时序图红色部分所示:
![]() 程序实现:
1
using System;2 ![]() 3 namespace KFC4 {5 /// <summary>6 /// FoodManager类,即指导者7 /// </summary>8 public class FoodManager9 {10 public void Construct(Builder builder)11 {12 builder.BuildHamb();13 ![]() 14 builder.BuildCoke();15 ![]() 16 builder.BuildChip();17 } 18 }19 }20 ![]() 3.建造者处理指导者的要求,并将部件添加到产品中。餐馆员工(建造者)按照收银员要求的把对应的汉堡,可乐,薯条放入盘子中。这部分是建造者模式里面富于变化的部分,因为顾客选择的套餐不同,套餐的组装过程也不同,这步完成产品对象的创建工作。
程序实现:
1 using System;2 ![]() 3 namespace KFC4 {5 /// <summary>6 /// Builder类,即抽象建造者类,构造套餐7 /// </summary>8 public abstract class Builder9 { 10 /// <summary>11 /// 添加汉堡12 /// </summary>13 public abstract void BuildHamb();14 15 /// <summary>16 /// 添加可乐17 /// </summary>18 public abstract void BuildCoke();19 20 /// <summary>21 /// 添加薯条22 /// </summary>23 public abstract void BuildChip();24 25 /// <summary>26 /// 返回结果27 /// </summary>28 /// <returns>食品对象</returns>29 public abstract Food GetFood();30 }31 }32 ![]() 1 using System;2 ![]() 3 namespace KFC4 {5 /// <summary>6 /// NormalBuilder类,具体构造者,普通套餐7 /// </summary>8 public class NormalBuilder:Builder9 {10 private Food NormalFood = new Food();11 ![]() 12 public override void BuildHamb()13 {14 NormalFood.Add("NormalHamb","¥10.50");15 }16 17 public override void BuildCoke()18 {19 NormalFood.Add("CokeCole","¥4.50");20 }21 ![]() 22 public override void BuildChip()23 {24 NormalFood.Add("FireChips","¥2.00");25 }26 ![]() 27 public override Food GetFood()28 {29 return NormalFood;30 }31 ![]() 32 }33 }34 ![]() 1 using System;2 ![]() 3 namespace KFC4 {5 /// <summary>6 /// GoldBuilder类,具体构造者,黄金套餐7 /// </summary>8 public class GoldBuilder:Builder9 {10 private Food GoldFood = new Food();11 ![]() 12 public override void BuildHamb()13 {14 GoldFood.Add("GoldHamb","¥13.50");15 }16 17 public override void BuildCoke()18 {19 GoldFood.Add("CokeCole","¥4.50");20 }21 ![]() 22 public override void BuildChip()23 {24 GoldFood.Add("FireChips","¥3.50");25 }26 ![]() 27 public override Food GetFood()28 {29 return GoldFood;30 }31 |



生活中的例子
实现过程图解
客户端:顾客。想去买一套套餐(这里面包括汉堡,可乐,薯条),可以有
程序实现:




}