当前位置: 首页 > news >正文

设计模式九:构建器模式 (Builder Pattern)

 动机(Motivation)

 1、在软件系统中,有时候面临着“一个复杂对象”的创建工作,其通常由各个部分的子对象用一定的算法构成;由于需求的变化,这个复杂对象的各个部分经常面临着剧烈的变化,但是将它们组合在一起的算法却相对稳定。
2、如何应对这种变化?如何提供一种“封装机制”来隔离出“复杂对象的各个部分”的变化,从而保持系统中的“稳定构建算法”不随着需求改变而改变?

 基本概念

定义:构建器模式是一种创建型设计模式,它允许您分步骤创建复杂对象,使得相同的构建过程可以创建不同的表示。

构建器模式的核心思想是将复杂对象的构建与其表示分离,使得:

  • 客户端不需要知道对象内部的具体组成细节

  • 相同的构建过程可以创建不同的表示

  • 可以更精细地控制对象的构建过程

实现方式

1. 经典构建器模式实现

#include <iostream>
#include <memory>
#include <string>// 最终要构建的产品
class Pizza {
public:void setDough(const std::string& dough) {dough_ = dough;}void setSauce(const std::string& sauce) {sauce_ = sauce;}void setTopping(const std::string& topping) {topping_ = topping;}void showPizza() const {std::cout << "Pizza with " << dough_ << " dough, "<< sauce_ << " sauce and "<< topping_ << " topping." << std::endl;}private:std::string dough_;std::string sauce_;std::string topping_;
};// 抽象构建器
class PizzaBuilder {
public:virtual ~PizzaBuilder() = default;Pizza* getPizza() {return pizza_.get();}void createNewPizza() {pizza_ = std::make_unique<Pizza>();}virtual void buildDough() = 0;virtual void buildSauce() = 0;virtual void buildTopping() = 0;protected:std::unique_ptr<Pizza> pizza_;
};// 具体构建器 -  HawaiianPizzaBuilder
class HawaiianPizzaBuilder : public PizzaBuilder {
public:void buildDough() override {pizza_->setDough("cross");}void buildSauce() override {pizza_->setSauce("mild");}void buildTopping() override {pizza_->setTopping("ham+pineapple");}
};// 具体构建器 - SpicyPizzaBuilder
class SpicyPizzaBuilder : public PizzaBuilder {
public:void buildDough() override {pizza_->setDough("pan baked");}void buildSauce() override {pizza_->setSauce("hot");}void buildTopping() override {pizza_->setTopping("pepperoni+salami");}
};// 指导者 (Director) - 控制构建过程
class Cook {
public:void setPizzaBuilder(PizzaBuilder* pb) {pizzaBuilder_ = pb;}Pizza* getPizza() {return pizzaBuilder_->getPizza();}void constructPizza() {pizzaBuilder_->createNewPizza();pizzaBuilder_->buildDough();pizzaBuilder_->buildSauce();pizzaBuilder_->buildTopping();}private:PizzaBuilder* pizzaBuilder_;
};int main() {Cook cook;// 构建 Hawaiian PizzaHawaiianPizzaBuilder hawaiianBuilder;cook.setPizzaBuilder(&hawaiianBuilder);cook.constructPizza();Pizza* hawaiianPizza = cook.getPizza();hawaiianPizza->showPizza();  // 输出: Pizza with cross dough, mild sauce and ham+pineapple topping.// 构建 Spicy PizzaSpicyPizzaBuilder spicyBuilder;cook.setPizzaBuilder(&spicyBuilder);cook.constructPizza();Pizza* spicyPizza = cook.getPizza();spicyPizza->showPizza();  // 输出: Pizza with pan baked dough, hot sauce and pepperoni+salami topping.return 0;
}

2. 流式接口构建器 (更现代的C++实现)

#include <iostream>
#include <memory>
#include <string>class Computer {
public:void setCPU(const std::string& cpu) { cpu_ = cpu; }void setRAM(const std::string& ram) { ram_ = ram; }void setStorage(const std::string& storage) { storage_ = storage; }void setGPU(const std::string& gpu) { gpu_ = gpu; }void showSpecs() const {std::cout << "Computer Specs:\n"<< "CPU: " << cpu_ << "\n"<< "RAM: " << ram_ << "\n"<< "Storage: " << storage_ << "\n"<< "GPU: " << (gpu_.empty() ? "Integrated" : gpu_) << "\n";}private:std::string cpu_;std::string ram_;std::string storage_;std::string gpu_;
};class ComputerBuilder {
public:ComputerBuilder() : computer_(std::make_unique<Computer>()) {}ComputerBuilder& setCPU(const std::string& cpu) {computer_->setCPU(cpu);return *this;}ComputerBuilder& setRAM(const std::string& ram) {computer_->setRAM(ram);return *this;}ComputerBuilder& setStorage(const std::string& storage) {computer_->setStorage(storage);return *this;}ComputerBuilder& setGPU(const std::string& gpu) {computer_->setGPU(gpu);return *this;}std::unique_ptr<Computer> build() {return std::move(computer_);}private:std::unique_ptr<Computer> computer_;
};int main() {// 使用流式接口构建计算机auto gamingPC = ComputerBuilder().setCPU("Intel i9-13900K").setRAM("32GB DDR5").setStorage("2TB NVMe SSD").setGPU("NVIDIA RTX 4090").build();gamingPC->showSpecs();auto officePC = ComputerBuilder().setCPU("AMD Ryzen 5").setRAM("16GB DDR4").setStorage("512GB SSD").build();  // 没有设置GPUofficePC->showSpecs();return 0;
}

 UML结构

 

构建器模式的优点

  1. 分步构建:可以分步骤构建复杂对象

  2. 复用构建过程:相同的构建过程可以创建不同的产品

  3. 单一职责原则:将复杂对象的构建代码与其业务逻辑分离

  4. 更好的控制:对构建过程有更精细的控制

  5. 可扩展性:添加新的具体构建器无需修改现有代码

适用场景

  1. 当创建复杂对象的算法应该独立于该对象的组成部分及其装配方式时

  2. 当构造过程必须允许被构造的对象有不同的表示时

  3. 当需要避免"伸缩构造函数"问题(构造函数参数过多)时

  4. 当对象有大量可选组件或配置时

构建器模式的变体

  1. 流式接口构建器:通过方法链提供更优雅的API

  2. Groovy风格构建器:利用C++运算符重载实现更自然的语法

  3. 组合构建器:多个构建器协同工作构建复杂对象

注意事项

  1. 构建器模式会增加代码复杂度,因为需要创建多个新类

  2. 对于简单对象,直接使用构造函数可能更合适

  3. 确保构建器在构建完成后不能被重复使用(除非显式重置)

构建器模式在C++中特别适合用于创建配置复杂的对象,特别是当对象有许多可选组件时。流式接口的实现方式使得代码更加清晰易读。

http://www.xdnf.cn/news/1172125.html

相关文章:

  • springboot 升级到3.5.x后knife4j 文档无法识别问题解决
  • 新手向:Idea的使用技巧
  • Kubernetes服务发布基础
  • 【数据结构】线性表概括
  • [特殊字符] 从数据库无法访问到成功修复崩溃表:一次 MySQL 故障排查实录
  • SQL基础⑧ | 表格篇
  • React中的antd的表格使用方法
  • 在 Ubuntu 上将 Docker 降级到版本 25.0.5 (二) 降低版本,涉及兼容性问题
  • 解决 i.MX6ULL 通过 ADB 连接时权限不足问题 not in the plugdev group
  • C++ 扫描局域网某个端口是否开放(如 5555 )(android adb) 线程并发加速
  • 苍穹外卖DAY11
  • 华为云数据库 GaussDB的 nvarchar2隐式类型转换的坑
  • gig-gitignore工具实战开发(一):项目愿景与蓝图规划
  • C#与WPF使用mvvm简单案例点击按钮触发弹窗
  • C Primer Plus 第6版 编程练习——第10章(上)
  • MySQL金融级数据一致性保障:从原理到实战
  • 视频、音频录制
  • Javascript常见的使用场景
  • 基于 XGBoost 与 SHAP 的医疗自动化办公与可视化系统(上)
  • Deep learning--模型压缩的五种方法
  • 什么是5G-A三防平板?有什么特点?哪些领域能用到?
  • Java 抽象类 vs 接口(Abstract Class vs Interface)对比笔记
  • 220V降5V,输出100MA,为家电电器消费类产品提供电源WD5202L
  • 【Dify】-进阶11- 权限与发布配置详解
  • ESP32-CAM实战:DIY基于OpenAI的AI视觉识别相机
  • 显微科研中的关键选择:不同显微镜相机技术特性与应用适配性全面解析
  • k8s pvc是否可绑定在多个pod上
  • 学生信息管理系统 - HTML实现增删改查
  • 硬件基础 -- 信号完整性
  • solidity从入门到精通 第四章:智能合约的生命周期