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

建造者模式-创建型

一、建造者模式

1.1、核心思想

将一个复杂对象的构建与它的表示分离,使得同样的构建过程可以创建不同的表示。<================>(说人话)创建步骤复杂,需要过多参数,用户只提供自己的参数,只关心最后的结果,不关心中间
的过程。比如diy主机:CPU:是考虑intel还是AMD:i5还是Rzen5 9700x等;内存是ddr5还是ddr4,选择哪个厂家,容量多大,时序多少等。

1.2、为什么需要建造者模式

问题场景

以DIY主机为例:

// 糟糕的设计:伸缩构造函数模式classComputer{public:// 构造函数1:只有必填参数Computer(conststring&cpu,conststring&ram):cpu_(cpu),ram_(ram){}// 构造函数2:加上可选参数Computer(conststring&cpu,conststring&ram,conststring&storage):cpu_(cpu),ram_(ram),storage_(storage){}// 构造函数3:再加上更多可选参数...Computer(conststring&cpu,conststring&ram,conststring&storage,conststring&gpu,conststring&monitor):cpu_(cpu),ram_(ram),storage_(storage),gpu_(gpu),monitor_(monitor){}// 更多构造函数...// 问题:参数太多,难以阅读和维护!private:string cpu_;string ram_;string storage_="";string gpu_="";string monitor_="";boolbluetooth_=false;// ... 更多成员};// 使用:哪个参数对应什么?完全看不懂!Computercomputer("i7","16GB","1TB SSD","RTX 3080","27寸4K",true,false,true);

问题点:

  1. 构造函数的参数太多,难以阅读和维护。
  2. 用户需要记住每个参数的顺序和类型,容易出错。
  3. 扩展性差,每次增加新属性都需要修改构造函数。

建造者模式解决方案

  1. 构建产品类
// 产品类:电脑classComputer{public:// 使用友元类,让Builder可以访问私有成员friendclassComputerBuilder;voidshow()const{std::cout<<"=== 电脑配置 ==="<<std::endl;std::cout<<"CPU: "<<cpu_<<std::endl;std::cout<<"内存: "<<ram_<<std::endl;if(!storage_.empty()){std::cout<<"存储: "<<storage_<<std::endl;}if(!gpu_.empty()){std::cout<<"显卡: "<<gpu_<<std::endl;}if(!monitor_.empty()){std::cout<<"显示器: "<<monitor_<<std::endl;}std::cout<<"蓝牙: "<<(bluetooth_?"支持":"不支持")<<std::endl;std::cout<<"WiFi: "<<(wifi_?"支持":"不支持")<<std::endl;std::cout<<"总价: ¥"<<price_<<std::endl;}private:// 私有构造函数,只能通过Builder创建Computer()=default;// 电脑组件std::string cpu_;std::string ram_;std::string storage_;std::string gpu_;std::string monitor_;boolbluetooth_=false;boolwifi_=false;doubleprice_=0.0;};
  1. 构建建造者类
// 抽象建造者classComputerBuilder{public:virtual~ComputerBuilder()=default;// 构建步骤virtualvoidbuildCPU(conststd::string&cpu)=0;virtualvoidbuildRAM(conststd::string&ram)=0;virtualvoidbuildStorage(conststd::string&storage)=0;virtualvoidbuildGPU(conststd::string&gpu)=0;virtualvoidbuildMonitor(conststd::string&monitor)=0;virtualvoidbuildBluetooth(boolenabled)=0;virtualvoidbuildWifi(boolenabled)=0;// 获取产品virtualstd::unique_ptr<Computer>getResult()=0;};
  1. 构建具体建造者类
// 具体建造者:游戏电脑建造者classGamingComputerBuilder:publicComputerBuilder{private:std::unique_ptr<Computer>computer_;public:GamingComputerBuilder(){computer_=std::make_unique<Computer>();computer_->price_=0.0;// 初始价格}voidbuildCPU(conststd::string&cpu)override{computer_->cpu_=cpu;computer_->price_+=(cpu.find("i9")!=std::string::npos)?3500:2500;std::cout<<"安装CPU: "<<cpu<<std::endl;}voidbuildRAM(conststd::string&ram)override{computer_->ram_=ram;computer_->price_+=(ram.find("32GB")!=std::string::npos)?1200:800;std::cout<<"安装内存: "<<ram<<std::endl;}voidbuildStorage(conststd::string&storage)override{computer_->storage_=storage;computer_->price_+=(storage.find("2TB")!=std::string::npos)?1500:800;std::cout<<"安装存储: "<<storage<<std::endl;}voidbuildGPU(conststd::string&gpu)override{computer_->gpu_=gpu;computer_->price_+=(gpu.find("RTX")!=std::string::npos)?5000:2000;std::cout<<"安装显卡: "<<gpu<<std::endl;}voidbuildMonitor(conststd::string&monitor)override{computer_->monitor_=monitor;computer_->price_+=(monitor.find("4K")!=std::string::npos)?2000:1000;std::cout<<"连接显示器: "<<monitor<<std::endl;}voidbuildBluetooth(boolenabled)override{computer_->bluetooth_=enabled;computer_->price_+=enabled?100:0;std::cout<<"配置蓝牙: "<<(enabled?"支持":"不支持")<<std::endl;}voidbuildWifi(boolenabled)override{computer_->wifi_=enabled;computer_->price_+=enabled?150:0;std::cout<<"配置WiFi: "<<(enabled?"支持":"不支持")<<std::endl;}std::unique_ptr<Computer>getResult()override{std::cout<<"游戏电脑组装完成!"<<std::endl;returnstd::move(computer_);}};// 具体建造者:办公电脑建造者classOfficeComputerBuilder:publicComputerBuilder{private:std::unique_ptr<Computer>computer_;public:OfficeComputerBuilder(){computer_=std::make_unique<Computer>();computer_->price_=0.0;}voidbuildCPU(conststd::string&cpu)override{computer_->cpu_=cpu;computer_->price_+=(cpu.find("i5")!=std::string::npos)?1200:800;std::cout<<"安装CPU: "<<cpu<<std::endl;}voidbuildRAM(conststd::string&ram)override{computer_->ram_=ram;computer_->price_+=400;// 办公电脑内存价格固定std::cout<<"安装内存: "<<ram<<std::endl;}voidbuildStorage(conststd::string&storage)override{computer_->storage_=storage;computer_->price_+=500;std::cout<<"安装存储: "<<storage<<std::endl;}voidbuildGPU(conststd::string&gpu)override{// 办公电脑默认集成显卡if(!gpu.empty()){computer_->gpu_=gpu;computer_->price_+=800;std::cout<<"安装显卡: "<<gpu<<std::endl;}}voidbuildMonitor(conststd::string&monitor)override{computer_->monitor_=monitor;computer_->price_+=800;std::cout<<"连接显示器: "<<monitor<<std::endl;}voidbuildBluetooth(boolenabled)override{computer_->bluetooth_=enabled;computer_->price_+=enabled?50:0;std::cout<<"配置蓝牙: "<<(enabled?"支持":"不支持")<<std::endl;}voidbuildWifi(boolenabled)override{computer_->wifi_=enabled;computer_->price_+=enabled?80:0;std::cout<<"配置WiFi: "<<(enabled?"支持":"不支持")<<std::endl;}std::unique_ptr<Computer>getResult()override{std::cout<<"办公电脑组装完成!"<<std::endl;returnstd::move(computer_);}};
  1. 指挥者(Director):指导构建过程,但不直接参与具体建造细节。
// 指挥者:指导构建过程classComputerDirector{public:voidconstructGamingComputer(ComputerBuilder&builder){std::cout<<"\n开始构建高性能游戏电脑..."<<std::endl;builder.buildCPU("Intel i9-13900K");builder.buildRAM("32GB DDR5");builder.buildStorage("2TB NVMe SSD");builder.buildGPU("NVIDIA RTX 4080");builder.buildMonitor("32寸4K 144Hz");builder.buildBluetooth(true);builder.buildWifi(true);}voidconstructOfficeComputer(ComputerBuilder&builder){std::cout<<"\n开始构建办公电脑..."<<std::endl;builder.buildCPU("Intel i5-12400");builder.buildRAM("16GB DDR4");builder.buildStorage("512GB SSD");builder.buildGPU("");// 集成显卡builder.buildMonitor("24寸1080P");builder.buildBluetooth(true);builder.buildWifi(true);}voidconstructBasicComputer(ComputerBuilder&builder){std::cout<<"\n开始构建基础电脑..."<<std::endl;builder.buildCPU("Intel i3-12100");builder.buildRAM("8GB DDR4");builder.buildStorage("256GB SSD");builder.buildMonitor("21.5寸1080P");// 不调用 buildGPU, buildBluetooth, buildWifi 使用默认值}};// 使用示例voiddemoBuilderPattern(){std::cout<<"=== 建造者模式演示 ==="<<std::endl;ComputerDirector director;// 构建游戏电脑GamingComputerBuilder gamingBuilder;director.constructGamingComputer(gamingBuilder);autogamingPC=gamingBuilder.getResult();gamingPC->show();// 构建办公电脑OfficeComputerBuilder officeBuilder;director.constructOfficeComputer(officeBuilder);autoofficePC=officeBuilder.getResult();officePC->show();// 自定义构建std::cout<<"\n=== 自定义构建 ==="<<std::endl;GamingComputerBuilder customBuilder;customBuilder.buildCPU("AMD Ryzen 7 7800X3D");customBuilder.buildRAM("64GB DDR5");customBuilder.buildStorage("4TB NVMe SSD");customBuilder.buildGPU("AMD RX 7900 XTX");customBuilder.buildMonitor("34寸曲面带鱼屏");customBuilder.buildBluetooth(true);customBuilder.buildWifi(true);autocustomPC=customBuilder.getResult();customPC->show();}

1.3、建造者模式常见的四个角色

  • Product(产品角色):一个具体的产品对象,比如上面的Computer
  • Builder(抽象建造者):定义构建步骤的接口,比如上面的ComputerBuilder
  • ConcreteBuilder(具体建造者):实现构建步骤,比如上面的GamingComputerBuilder,OfficeComputerBuilder
  • Director(指挥者):指导构建过程以及隔离客户与对象的生产过程,比如上面的ComputerDirector

附上UML类图:

二、总结

2.1、优缺点

优点缺点
构造过程清晰可控增加了代码复杂度
避免伸缩构造函数需要创建多个类
可以分布构建对象适合复杂对象,简单对象不划算
更好的参数验证产品类需要暴露给建造者

2.2、适用场景

  1. 创建复杂对象:对象有很多组成部分,构造过程复杂
  2. 构造过程需要精细控制:需要细化构建步骤
  3. 对象有很多可选参数
  4. 需要创建不同表示的对象:同样的构建过程,不同的配置

2.3、建造者模式 VS 工厂模式

  • 工厂模式:侧重于创建对象,不关心构建过程
  • 建造者模式:侧重于构建过程,不关心对象类型
http://www.gsyq.cn/news/111736.html

相关文章:

  • TypedArray 详解
  • 【课程设计/毕业设计】基于Java兽医站管理系统基于JavaWeb的兽医站管理系统的设计与实现【附源码、数据库、万字文档】
  • DNP3.0学习记录
  • kanass全面介绍(12) - 如何自定义事项类型,满足个性化需求
  • 打了一堆板子,才发现是VDD_EXT的锅
  • 28.封装 map set (下)
  • 还买啥USB网卡~直接开启RNDIS就行
  • 2026年EOR名义雇主服务优势TOP8对比榜单,助力全球化布局与用工优化
  • 实用指南:(113页PPT)西门子制造业研发工艺协同平台及制造平台整体规划(附下载方式)
  • Vue低代码平台实测红黑榜:别让“伪效率“消耗你的团队
  • 【课程设计/毕业设计】基于SpringBoot+Vue茶叶销售系统的设计与实现基于Java语言的茶叶销售系统的前端设计与实现【附源码、数据库、万字文档】
  • 构建高效测试体系:测试文档编写规范详解
  • 第四章算法作业
  • 版本升级|Origin 2026 科学绘图与数据分析软件
  • 播放器视频后处理实践(二)氛围模式
  • 【课程设计/毕业设计】基于springboot/javaEE的二手手机交易平台的设计与实现基于javaEE的二手手机交易平台的设计与实现【附源码、数据库、万字文档】
  • K-Means聚类+PCA降维:高维数据聚类的最优组合实战指南
  • SQL 调优全解:从 20 秒到 200 ms 的 6 步实战笔记(附脚本)
  • [THUPC 2024 初赛] 一棵树
  • Linux入门(更新中...)
  • 三相异步电动机启保停正反转星三角控制电路及西门子200PLC与MCGS7.7联机程序(带注释和...
  • Ubuntu22.04安装postgresql16.8
  • 如何修复 Element Plus Table 在分页切换时滚动条不更新的问题
  • 水塔液位控制系统实战手记
  • OE 平台是什么?基于多来源数字内容管理需求形成的海外工具型平台
  • 新的spring boot3.x和spring-security6.x的流程
  • 西门子Wincc报表模版大全:多种模板积攒,视频讲解详解,SQL数据库应用实战
  • 从“水往低处流”到“逆流而上”:BFS搜索巧解太平洋大西洋水流问题
  • LobeChat能否实现AI生成季度报告?财务与业务总结自动化
  • CPS 信息物理系统:世界模型的基础与人工智能万物互联控制的实现​