1 建造者模式简介
1.1 定义
建造者模式(Builder)将复杂的构建与其表示相分离,使得同样的构建过程可以创建不同的表示。
1.2 使用频率
中低
2 建造者模式结构
2.1 结构图
2.2 参与者
建造者模式参与者:
◊ Builder:为创建一个Product对象的各个部件指定抽象接口;
◊ ConcreteBuilder
° 实现Builder的接口以构造和装配该产品的各个部件
° 定义并明确它所创建的表示
° 提供一个检索Product的接口
◊ Director:构造一个使用Builder接口的对象;
◊ Product
° 表示被构造的复杂对象。ConcreteBuilder创建该产品的内部表示并定义它的装配过程
° 包含定义组成部件的类,包括将这些部件装配成最终产品的接口
在建造者模式中,Director规定了创建一个对象所需要的步骤和次序,Builder则提供了一些列完成这些步骤的方法,ConcreteBuilder给出了这些方法的具体实现,是对象的直接创建者。
3 建造者模式结构实现
Product.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.BuilderPattern.Structural
{
public class Product
{
private List<string> _parts = new List<string>(); public void Add(string part)
{
_parts.Add(part);
} public void Show()
{
Console.WriteLine("Product Parts");
foreach (string part in _parts)
{
Console.WriteLine(part);
}
}
}
}
Builder.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.BuilderPattern.Structural
{
public abstract class Builder
{
public abstract void BuildPartA();
public abstract void BuildPartB();
public abstract Product GetResult();
}
}
ConcreteBuilder1.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.BuilderPattern.Structural
{
public class ConcreteBuilder1 : Builder
{
private Product _product = new Product(); public override void BuildPartA()
{
_product.Add("PartA");
} public override void BuildPartB()
{
_product.Add("PartB");
} public override Product GetResult()
{
return _product;
}
}
}
ConcreteBuilder2.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.BuilderPattern.Structural
{
public class ConcreteBuilder2 : Builder
{
private Product _product = new Product(); public override void BuildPartA()
{
_product.Add("PartX");
} public override void BuildPartB()
{
_product.Add("PartY");
} public override Product GetResult()
{
return _product;
}
}
}
Director.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.BuilderPattern.Structural
{
public class Director
{
/// <summary>
/// Builder uses a complex series of steps
/// </summary>
public void Construct(Builder builder)
{
builder.BuildPartA();
builder.BuildPartB();
}
}
}
Program.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; using DesignPatterns.BuilderPattern.Structural; namespace DesignPatterns.BuilderPattern
{
class Program
{
static void Main(string[] args)
{
// Create director and builders
Director director = new Director(); Builder b1 = new ConcreteBuilder1();
Builder b2 = new ConcreteBuilder2(); // Construct two products
director.Construct(b1);
Product p1 = b1.GetResult();
p1.Show(); director.Construct(b2);
Product p2 = b2.GetResult();
p2.Show();
}
}
}
运行输出:
Product Parts
PartA
PartB
Product Parts
PartX
PartY
请按任意键继续. . .
4、建造者模式实践应用
Vehicle.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.BuilderPattern.Practical
{
/// <summary>
/// The 'Product' class
/// </summary>
public class Vehicle
{
private string _vehicleType;
private Dictionary<string, string> _parts = new Dictionary<string, string>(); /// <summary>
/// Constructor
/// </summary>
public Vehicle(string vehicleType)
{
this._vehicleType = vehicleType;
} /// <summary>
/// Indexer
/// </summary>
public string this[string key]
{
get { return _parts[key]; }
set { _parts[key] = value; }
} public void Show()
{
Console.WriteLine("\n---------------------------");
Console.WriteLine("Vehicle Type: {0}", _vehicleType);
Console.WriteLine(" Frame : {0}", _parts["frame"]);
Console.WriteLine(" Engine : {0}", _parts["engine"]);
Console.WriteLine(" #Wheels: {0}", _parts["wheels"]);
Console.WriteLine(" #Doors : {0}", _parts["doors"]);
}
}
}
VehicleBuilder.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.BuilderPattern.Practical
{
/// <summary>
/// The 'Builder' abstract class
/// </summary>
public abstract class VehicleBuilder
{
protected Vehicle vehicle; // Gets vehicle instance
public Vehicle Vehicle
{
get { return vehicle; }
} // Abstract build methods
public abstract void BuildFrame();
public abstract void BuildEngine();
public abstract void BuildWheels();
public abstract void BuildDoors();
}
}
MotorCycleBuilder.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.BuilderPattern.Practical
{
public class MotorCycleBuilder : VehicleBuilder
{
public MotorCycleBuilder()
{
vehicle = new Vehicle("MotorCycle");
} public override void BuildFrame()
{
vehicle["frame"] = "MotorCycle Frame";
} public override void BuildEngine()
{
vehicle["engine"] = "500 cc";
} public override void BuildWheels()
{
vehicle["wheels"] = "";
} public override void BuildDoors()
{
vehicle["doors"] = "";
}
}
}
CarBuilder.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.BuilderPattern.Practical
{
public class CarBuilder : VehicleBuilder
{
public CarBuilder()
{
vehicle = new Vehicle("Car");
} public override void BuildFrame()
{
vehicle["frame"] = "Car Frame";
} public override void BuildEngine()
{
vehicle["engine"] = "2500 cc";
} public override void BuildWheels()
{
vehicle["wheels"] = "";
} public override void BuildDoors()
{
vehicle["doors"] = "";
}
}
}
ScooterBuilder.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.BuilderPattern.Practical
{
public class ScooterBuilder : VehicleBuilder
{
public ScooterBuilder()
{
vehicle = new Vehicle("Scooter");
} public override void BuildFrame()
{
vehicle["frame"] = "Scooter Frame";
} public override void BuildEngine()
{
vehicle["engine"] = "50 cc";
} public override void BuildWheels()
{
vehicle["wheels"] = "";
} public override void BuildDoors()
{
vehicle["doors"] = "";
}
}
}
Shop.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.BuilderPattern.Practical
{
public class Shop
{
public void Construct(VehicleBuilder vehicleBuilder)
{
vehicleBuilder.BuildFrame();
vehicleBuilder.BuildEngine();
vehicleBuilder.BuildWheels();
vehicleBuilder.BuildDoors();
}
}
}
Program.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; using DesignPatterns.BuilderPattern.Practical; namespace DesignPatterns.BuilderPattern
{
class Program
{
static void Main(string[] args)
{
VehicleBuilder builder;
// Create shop with vehicle builders
Shop shop = new Shop(); // Construct and display vehicles
builder = new ScooterBuilder();
shop.Construct(builder);
builder.Vehicle.Show(); builder = new CarBuilder();
shop.Construct(builder);
builder.Vehicle.Show(); builder = new MotorCycleBuilder();
shop.Construct(builder);
builder.Vehicle.Show();
}
}
}
运行输出:
---------------------------
Vehicle Type: Scooter
Frame : Scooter Frame
Engine : cc
#Wheels:
#Doors : ---------------------------
Vehicle Type: Car
Frame : Car Frame
Engine : cc
#Wheels:
#Doors : ---------------------------
Vehicle Type: MotorCycle
Frame : MotorCycle Frame
Engine : cc
#Wheels:
#Doors :
请按任意键继续. . .
5 建造者模式应用分析
建造者模式适用情形:
◊ 需要生成的产品对象有复杂的内部结构
◊ 需要生成的产品对象的属性相互依赖,建造者模式可以强迫生成顺序
◊ 在对象创建过程中会使用到系统中的一些其他对象,这些对象在产品对象的创建过程中不易得到
建造者模式特点:
◊ 建造者模式的使用使得产品的内部表对象可以独立地变化。使用建造者模式可以使客户不必知道产品内部组成的细节
◊ 每一个Builder都相对独立,而与其他Builder无关
◊ 可使对构造过程更加精细控制
◊ 将构建代码和表示代码分开
◊ 建造者模式的缺点在于难于应付分步骤构建算法的需求变动