首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> .NET 網頁程式設計 >> C# >> 關於C#

C# 設計模式深度解析:建造者模式

     編輯:關於C#

一、建造者模式:將構建過程與內部表示分離

當對象擁有重要屬性且須按特定順序賦值,或屬性間存在依賴時,構建邏輯變得複雜。建造者模式將此「零件組裝過程」外部化到建造者對象,客戶端獲得的是完整構建好的產品。名為「建造」而非「生成」,強調從零件組裝產品的過程性。

二、四大角色結構

建造者模式結構圖

  1. 建造者角色:抽象介面,規範產品各組成部分的建造步驟,獨立於業務邏輯。
  2. 具體建造者角色:實現建造介面,逐步構建產品實例,完成後提供產品引用。
  3. 指導者角色:調用具體建造者創建產品,掌握構建順序,不知曉具體產品細節。
  4. 產品角色:被構建的複雜對象。

指導者將客戶請求分解為零件建造請求,委派給具體建造者;具體建造者執行具體工作,對客戶端透明。

三、結構型示例

// Builder pattern -- Structural example
using System; using System.Collections;

class Director {
    public void Construct(Builder builder) {
        builder.BuildPartA(); builder.BuildPartB();
    }
}

abstract class Builder {
    abstract public void BuildPartA();
    abstract public void BuildPartB();
    abstract public Product GetResult();
}

class ConcreteBuilder1 : Builder {
    private Product product;
    override public void BuildPartA() { product = new Product(); product.Add("PartA"); }
    override public void BuildPartB() { product.Add("PartB"); }
    override public Product GetResult() { return product; }
}

class ConcreteBuilder2 : Builder {
    private Product product;
    override public void BuildPartA() { product = new Product(); product.Add("PartX"); }
    override public void BuildPartB() { product.Add("PartY"); }
    override public Product GetResult() { return product; }
}

class Product {
    ArrayList parts = new ArrayList();
    public void Add(string part) { parts.Add(part); }
    public void Show() {
        Console.WriteLine("Product Parts -------");
        foreach (string part in parts) Console.WriteLine(part);
    }
}

public class Client {
    public static void Main() {
        Director director = new Director();
        Builder b1 = new ConcreteBuilder1(), b2 = new ConcreteBuilder2();
        director.Construct(b1); b1.GetResult().Show();
        director.Construct(b2); b2.GetResult().Show();
    }
}

四、實戰應用:車輛製造工廠

// Builder pattern -- Real World example
using System; using System.Collections;

class Shop {
    public void Construct(VehicleBuilder vb) {
        vb.BuildFrame(); vb.BuildEngine(); vb.BuildWheels(); vb.BuildDoors();
    }
}

abstract class VehicleBuilder {
    protected Vehicle vehicle;
    public Vehicle Vehicle { get { return vehicle; } }
    abstract public void BuildFrame();
    abstract public void BuildEngine();
    abstract public void BuildWheels();
    abstract public void BuildDoors();
}

class MotorCycleBuilder : VehicleBuilder {
    override public void BuildFrame() { vehicle = new Vehicle("MotorCycle"); vehicle["frame"] = "MotorCycle Frame"; }
    override public void BuildEngine() { vehicle["engine"] = "500 cc"; }
    override public void BuildWheels() { vehicle["wheels"] = "2"; }
    override public void BuildDoors() { vehicle["doors"] = "0"; }
}

class CarBuilder : VehicleBuilder {
    override public void BuildFrame() { vehicle = new Vehicle("Car"); vehicle["frame"] = "Car Frame"; }
    override public void BuildEngine() { vehicle["engine"] = "2500 cc"; }
    override public void BuildWheels() { vehicle["wheels"] = "4"; }
    override public void BuildDoors() { vehicle["doors"] = "4"; }
}

class ScooterBuilder : VehicleBuilder {
    override public void BuildFrame() { vehicle = new Vehicle("Scooter"); vehicle["frame"] = "Scooter Frame"; }
    override public void BuildEngine() { vehicle["engine"] = "none"; }
    override public void BuildWheels() { vehicle["wheels"] = "2"; }
    override public void BuildDoors() { vehicle["doors"] = "0"; }
}

class Vehicle {
    private string type; private Hashtable parts = new Hashtable();
    public Vehicle(string type) { this.type = type; }
    public object this[string key] { get { return parts[key]; } set { parts[key] = value; } }
    public void Show() {
        Console.WriteLine("---------------------------");
        Console.WriteLine("Vehicle Type: " + type);
        Console.WriteLine(" Frame : " + parts["frame"]);
        Console.WriteLine(" Engine : " + parts["engine"]);
        Console.WriteLine(" #Wheels: " + parts["wheels"]);
        Console.WriteLine(" #Doors : " + parts["doors"]);
    }
}

public class BuilderApp {
    public static void Main() {
        Shop shop = new Shop();
        VehicleBuilder b1 = new ScooterBuilder(), b2 = new CarBuilder(), b3 = new MotorCycleBuilder();
        shop.Construct(b1); b1.Vehicle.Show();
        shop.Construct(b2); b2.Vehicle.Show();
        shop.Construct(b3); b3.Vehicle.Show();
    }
}

五、模式演化與變體

1. 省略抽象建造者

僅有一個具體建造者時,可移除抽象介面,指導者直接依賴具體類。

2. 省略指導者

若抽象建造者已省略,可讓建造者自身承擔指導者職責(如 StringBuilder):

public class Builder {
    private Product product = new Product();
    public void BuildPartA() { /* ... */ }
    public void BuildPartB() { /* ... */ }
    public Product GetResult() { return product; }
    public void Construct() { BuildPartA(); BuildPartB(); }
}

六、適用場景與優勢

適用場景:

  • 產品對象擁有複雜內部結構。
  • 屬性間相互依賴,需強制構建順序。
  • 構建過程需用到難以直接獲取的其他系統對象。

核心優勢:

  1. 產品內部表示可獨立變化,客戶端無需知曉構建細節。
  2. 各建造者相互獨立,易於新增或替換。
  3. 構建過程可控,最終產品更易管控。
  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved