设计模式(十四)之建造者模式

16 篇文章 0 订阅
16 篇文章 0 订阅

建造者模式(Builder):

将一个复杂对象的构建与它的表示分离,使得同样的构建过程可以创建不同的表示

使用角色:

Builder(抽象建造者)

ConcreteBuilder(具体建造者,可能有多个)

Product(产品)

Director(指挥者)

建造者UML图:
在这里插入图片描述

建造者模式精髓:建造者模式使得建造代码与表示代码的分离,可以使客户端不必知道产品内部组成的细节,从而降低了客户端与具体产品之间的耦合度。

建造者模式实现:

我去饭店吃饭,饭店的招牌菜是西红柿炒鸡蛋,饭店很火,有多位厨师(建造者类),为了避免,多个厨师做出多种口味的菜,店家将制作时需要添加的材料做成了一个秘制菜谱(建造类),厨师只要按照菜谱做,菜谱上详细的说明了材料的放置顺序,必须是先放西红柿,再放鸡蛋,再放糖,口味就不会有偏差。我去饭店吃饭,我不需要关心你的菜是怎么做出来的,我只需要告诉服务员(指挥者类)我要吃西红柿炒鸡蛋(产品),他把菜给我端上来就行了。

上代码:

产品类:Product.cs

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
  
namespace Builder
{
    /// <summary>
    /// 产品类
    /// </summary>
    public class Product
    {
        /// <summary>
        /// 产品列表
        /// </summary>
        public List<string> productList = new List<string>();
        /// <summary>
        /// 添加
        /// </summary>
        /// <param name="name"></param>
        public void add(string name)
        {
            productList.Add(name);
        }
        /// <summary>
        /// 展示
        /// </summary>
        public void show()
        {
            for (int i = 0; i < productList.Count; i++)
            {
                Console.WriteLine(productList[i]);
            }
        }
    }
}

建造者类:Builder.cs

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
  
namespace Builder
{
    /// <summary>
    /// 建造者类
    /// </summary>
    public abstract class Builder
    {
        /// <summary>
        /// 放西红柿
        /// </summary>
        public abstract void cai();
  
        /// <summary>
        /// 放糖
        /// </summary>
        public abstract void tang();
  
        /// <summary>
        /// 放鸡蛋
        /// </summary>
        public abstract void dan();
  
        /// <summary>
        /// 返回产品
        /// </summary>
        /// <returns></returns>
        public abstract Product GetResult();
    }
}

具体建造者类:BuilderOne.cs

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
  
namespace Builder
{
    class BuilderOne:Builder
    {
        /// <summary>
        /// 建造者二
        /// </summary>
        public Product pro = new Product();
  
        /// <summary>
        /// 放西红柿
        /// </summary>
        public override void cai()
        {
            pro.productList.Add("大厨放西红柿");
        }
  
        /// <summary>
        /// 放糖
        /// </summary>
        public override void tang()
        {
            pro.productList.Add("大厨放糖");
        }
  
        /// <summary>
        /// 放鸡蛋
        /// </summary>
        public override void dan()
        {
            pro.productList.Add("大厨放鸡蛋");
        }
  
  
        public override Product GetResult()
        {
            return pro;
        }
  
    }
}

具体建造者类2:BuilderTwo.cs

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
  
namespace Builder
{
    class BuilderTwo:Builder
    {
        /// <summary>
        /// 建造者一
        /// </summary>
        public Product pro = new Product();
        /// <summary>
        /// 放西红柿
        /// </summary>
        public override void cai()
        {
            pro.productList.Add("二厨放西红柿");
        }
  
        /// <summary>
        /// 放糖
        /// </summary>
        public override void tang()
        {
            pro.productList.Add("二厨放糖");
        }
  
        /// <summary>
        /// 放鸡蛋
        /// </summary>
        public override void dan()
        {
            pro.productList.Add("二厨放鸡蛋");
        }
  
  
        public override Product GetResult()
        {
            return pro;
        }
    }
}

指挥者类:负责指挥建造过程Director.cs

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
  
namespace Builder
{
    /// <summary>
    /// 建造类
    /// </summary>
    public class Director
    {
        /// <summary>
        /// 指挥建造过程(不向客人展示建造过程)
        /// </summary>
        /// <param name="build"></param>
        public void waiter(Builder build)
        {
            build.cai();
            build.dan();
            build.tang();
        }
    }
}

客户端:Program.cs

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
  
namespace Builder
{
    class Program
    {
        static void Main(string[] args)
        {
            // 两个客人同时点了西红柿炒鸡蛋,大厨和二厨依次接单做
  
            // 大厨
            Builder build_one = new BuilderOne();
            // 二厨
            Builder build_two = new BuilderTwo();
            // 指挥者类
            Director dir = new Director();
  
            // 指挥大厨做饭
            dir.waiter(build_one);
            // 做完饭
            Product p1 = build_one.GetResult();
            // 上菜
            p1.show();
  
            Console.WriteLine("大厨上菜");
            Console.WriteLine("----------------------------------------");
            // 指挥二厨做饭
            dir.waiter(build_two);
            // 做完饭
            Product p2 = build_two.GetResult();
            // 上菜
            p2.show();
            Console.WriteLine("二厨上菜");
            Console.ReadLine();
        }
    }
}

结果如下图所示:
在这里插入图片描述

建造者模式应用分析

建造者模式适用情形:

1:需要生成的产品对象有复杂的内部结构
:2: 需要生成的产品对象的属性相互依赖,建造者模式可以强迫生成顺序
3: 在对象创建过程中会使用到系统中的一些其他对象,这些对象在产品对象的创建过程中不易得到

建造者模式特点:

1: 建造者模式的使用使得产品的内部表对象可以独立地变化。使用建造者模式可以使客户不必知道产品内部组成的细节
2: 每一个Builder都相对独立,而与其他Builder无关
3:可使对构造过程更加精细控制
:4: 将构建代码和表示代码分开
5: 建造者模式的缺点在于难于应付分步骤构建算法的需求变动

有好的建议,请在下方输入你的评论。
欢迎访问个人博客
https://guanchao.site

欢迎访问小程序:

在这里插入图片描述

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值