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

設計模式實作系列(三):Builder 建造者模式 - 將複雜物件構建與表示分離

     編輯:關於C++

模式意圖

將一個複雜物件的構建與它的表示分離,使得同樣的構建過程可以創建不同的表示。

UML 結構圖

Builder Pattern UML

適用情境

  • 建構演算法應獨立於物件組成部分及其裝配方式。
  • 構造過程必須允許被構造物件有不同表示。

核心解析

  • Builder: 抽象基類定義構建步驟介面 BuildPartA(), BuildPartB()。
  • ConcreteBuilder: 實作具體構建邏輯,內部組裝產品。
  • Director: 控制構建流程 Construct(),呼叫 Builder 步驟,不依賴具體 Builder。
  • 關鍵: 「同樣流程、不同表示」——Director 固定順序,Builder 決定細節。

C++ 完整實作

1. Builder.h

#ifndef BUILDER_H
#define BUILDER_H

class Builder {
public:
    Builder() {}
    virtual ~Builder() {}
    virtual void BuildPartA() = 0;
    virtual void BuildPartB() = 0;
};

class Director {
public:
    Director(Builder* pBuilder);
    ~Director();
    void Construct();
private:
    Builder* m_pBuilder;
};

class ConcreteBuilder1 : public Builder {
public:
    ConcreteBuilder1() {}
    virtual ~ConcreteBuilder1() {}
    virtual void BuildPartA();
    virtual void BuildPartB();
};

class ConcreteBuilder2 : public Builder {
public:
    ConcreteBuilder2() {}
    virtual ~ConcreteBuilder2() {}
    virtual void BuildPartA();
    virtual void BuildPartB();
};

#endif

2. Builder.cpp

#include "Builder.h"
#include <iostream>

void ConcreteBuilder1::BuildPartA() { std::cout << "BuildPartA by ConcreteBuilder1\n"; }
void ConcreteBuilder1::BuildPartB() { std::cout << "BuildPartB by ConcreteBuilder1\n"; }
void ConcreteBuilder2::BuildPartA() { std::cout << "BuildPartA by ConcreteBuilder2\n"; }
void ConcreteBuilder2::BuildPartB() { std::cout << "BuildPartB by ConcreteBuilder2\n"; }

Director::Director(Builder* pBuilder) : m_pBuilder(pBuilder) {}
Director::~Director() { delete m_pBuilder; m_pBuilder = nullptr; }
void Director::Construct() {
    m_pBuilder->BuildPartA();
    m_pBuilder->BuildPartB();
}

3. Main.cpp

#include "Builder.h"
#include <cstdlib>

int main() {
    Builder* pBuilder1 = new ConcreteBuilder1();
    Director* pDirector1 = new Director(pBuilder1);
    pDirector1->Construct();

    Builder* pBuilder2 = new ConcreteBuilder2();
    Director* pDirector2 = new Director(pBuilder2);
    pDirector2->Construct();

    delete pDirector1; delete pDirector2;
    return 0;
}

Builder vs Abstract Factory

維度BuilderAbstract Factory
焦點複雜物件「分步驟構建過程」「系列相關物件」創建
回傳時機構建完成後一次取得產品每個創建方法即時回傳
流程控制Director 掌握順序客戶端自行決定順序
典型案例文檔轉換(HTML/PDF/RTF)、SQL 查詢建構器、HTTP 請求建構器跨平台 UI 元件庫、資料庫驅動族群

現代 C++:流式介面

class HttpRequestBuilder {
    HttpRequest req;
public:
    HttpRequestBuilder& SetUrl(string url) { req.url = url; return *this; }
    HttpRequestBuilder& AddHeader(string k, string v) { req.headers[k] = v; return *this; }
    HttpRequestBuilder& SetBody(string body) { req.body = body; return *this; }
    HttpRequest Build() { return std::move(req); }
};

// 使用
auto req = HttpRequestBuilder()
    .SetUrl("https://api.example.com")
    .AddHeader("Auth", "token")
    .SetBody("{}")
    .Build();

適用場景

  • 參數眾多、可選參數複雜的物件建構(避免建構子望遠鏡)。
  • 不可變物件建構(建構完成後凍結狀態)。
  • 多種表示格式共用構建邏輯(如報表匯出 PDF/Excel/CSV)。
  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved