【16】c++设计模式——>建造者(生成器)模式

什么是建造者模式?

建造者模式(Builder Pattern)是一种创建型设计模式,它允许你构造复杂对象步骤分解。你可以不同的步骤中使用不同的方式创建对象,且对象的创建与表示是分离的。这样,同样的构建过程可以创建不同的表示。
在 C++ 中,建造者模式通常涉及到以下几个关键部分:
1.产品(Product):这是最终要构造的对象。它通常包含很多属性。
2.抽象建造者(Abstract Builder):这是一个接口,定义了创建产品所需的各个步骤的方法。
3.具体建造者(Concrete Builder):这是实现抽象建造者接口的具体类。它实现了创建产品所需的各个步骤。
4.导演(Director):这个类负责执行创建产品的整个过程。它使用具体建造者来创建产品的各个部分,并在适当的时候调用它们。

建造者模式和工厂模式的区别?

建造者模式和工厂模式都是创建型设计模式,但它们的关注点和用途有所不同。以下是它们的主要区别:
1.关注点建造者模式注重零部件的组装过程,而工厂方法模式更注重零部件的创建过程
2.创建对象的力度:建造者模式创建复杂的对象,由各种复杂的部件组成,而工厂模式创建出来的对象都一样。
3.顺序:建造者模式根据建造过程中的顺序不一样,最终的对象部件组成也不一样。而工厂模式则没有这样的关注。
4.使用场景:创建简单对象时,通常使用工厂模式;创建复杂对象时,可以考虑使用建造者模式。
总的来说,工厂模式更注重对象的创建,而建造者模式更注重对象的组装过程和组成部分。在实际应用中,可以根据需要选择使用哪种设计模式。

建造者模式适用什么场景,举个具体的例子

建造者模式适用于创建具有多个组成部分的复杂对象,尤其是那些需要对个步骤来创建的对象。
假设我们需要创建一个复杂的“电脑”对象,该对象包含多个组成部分,如“CPU”、“内存”、“硬盘”等。我们可以使用建造者模式来创建这个对象,具体步骤如下:
1.首先我们需要一个产品类Computer ,也就是电脑,这是最终要构造的对象,电脑通常包含很多属性也就是组成部分,比如CPU,内存,硬盘这些;例如,在具体电脑建造者中,我们可以调用“Computer”类的“setCPU()”、“setMemory()”和“setHardDisk()”方法来设置电脑的各个组成部分
2.然后,我们定义一个抽象建造者ComputerBuilder接口,该接口定义了创建电脑对象所需的各个步骤的虚方法。如“buildCPU()”、“buildMemory()”、“buildHardDisk()”等。
3.接下来,我们定义一个具体建造者ConcreteComputerBuilder类,该类实现了抽象建造者接口中定义的所有方法。在具体建造者中,我们可以按照需要的顺序和方式来创建电脑对象的各个组成部分。
4.然后,我们定义一个导演ComputerDirector类,该类负责执行创建电脑对象的整个过程。导演类中使用具体建造者来创建电脑对象的各个部分,并在适当的时候调用它们。
5.最后,客户端代码可以使用导演类来创建电脑对象。客户端不需要知道电脑对象内部的具体实现细节,只需要调用导演类提供的方法即可。
代码示例:

#include<iostream>
#include<string>
using namespace std;//1.产品:电脑
class Computer
{
public:void setCPU(string cpu) { m_cpu = cpu; }void setMemory(string memory) { m_memory = memory; }void setHardDisk(string hardDisk) { m_hardDisk = hardDisk; }//const位于函数参数列表之后,表示该函数是一个常量成员函数,该函数不会修改任何成员变量的值void print()const {   std::cout << "CPU: " << m_cpu << ", Memory: " << m_memory << ", Hard Disk: " << m_hardDisk << std::endl;}
private:string m_cpu;string m_memory;string m_hardDisk;
};
//2.抽象建造者:电脑建造者接口
class ComputerBuilder
{
public:virtual ~ComputerBuilder() {}; //虚析构,为了销毁父类指针所指向的子类对象virtual void buildCPU() = 0; virtual void buildMemory() = 0;virtual void buildHardDisk() = 0;virtual Computer* getComputer() = 0;
};
//3.具体建造者:具体的电脑建造者
class  ConcreteComputerBuilder :public ComputerBuilder
{
public:void buildCPU() { m_computer->setCPU("Intel Core i7"); }void buildMemory() { m_computer->setMemory("16GB DDR4");}void buildHardDisk() { m_computer->setHardDisk("1TB SSD");}Computer* getComputer() { return m_computer; }private:Computer* m_computer = new Computer;
};
//4.导演:电脑建造导演
class ComputerDirector
{
public:ComputerDirector(ComputerBuilder* builder) :m_builder(builder) {}void construct() {m_builder->buildCPU();m_builder->buildMemory();m_builder->buildHardDisk();}
private:ComputerBuilder* m_builder;
};
int main()
{ConcreteComputerBuilder builder;//创建一个具体的电脑对象ComputerDirector director(&builder); //创建一个导演director.construct();builder.getComputer()->print();delete builder.getComputer();return 0;
}

在这里插入图片描述

手机生产

我现在要生产iphone手机,有iPhone14和iPhone15,各自又有mini和pro两个版本。

#include <iostream>
#include <memory>//产品类:iphone
class iPhone
{
public:void setMemory(const std::string& memory) { m_memory = memory; }void setScreen(const std::string& screen) { m_screen = screen; }void setAppearance(const std::string& apperance) { m_appearance = apperance; }void showInfo() const {std::cout << "Memory: " << m_memory << std::endl;std::cout << "Screen: " << m_screen << std::endl;std::cout << "Appearance: " << m_appearance << std::endl;}
private:std::string m_memory;std::string m_screen;std::string m_appearance;
};
//抽象建造者:iphone手机建造者接口
class iPhoneBuilder
{
public:virtual void buildMemory() = 0;virtual void buildScreen() = 0;virtual void buildAppearance() = 0;virtual std::unique_ptr<iPhone> getiPhone() = 0;};
//具体建造者:iPhone14 Mini 建造者
class iPhoneBuilder14Mini :public iPhoneBuilder
{void buildMemory() { m_memory = "64GB"; }void buildScreen() { m_screen = "5.4-inch"; }void buildAppearance() { m_appearance = "Glass back and aluminum frame"; };std::unique_ptr<iPhone>  getiPhone() override{std::unique_ptr<iPhone> iphone = std::make_unique<iPhone>();iphone->setMemory(m_memory);iphone->setScreen(m_screen);iphone->setAppearance(m_appearance);return iphone;}private:std::string m_memory;std::string m_screen;std::string m_appearance;
};//具体建造者:iPhone14 pro 建造者
class iPhoneBuilder14PRO :public iPhoneBuilder
{void buildMemory() { m_memory = "256GB"; }void buildScreen() { m_screen = "6.1-inch"; }void buildAppearance() { m_appearance = "Ceramic back and stainless steel frame"; };std::unique_ptr<iPhone>  getiPhone() override{std::unique_ptr<iPhone> iphone = std::make_unique<iPhone>();iphone->setMemory(m_memory);iphone->setScreen(m_screen);iphone->setAppearance(m_appearance);return iphone;}
private:std::string m_memory;std::string m_screen;std::string m_appearance;
};//导演类:生成手机
class Director 
{
public:std::unique_ptr<iPhone> create(iPhoneBuilder& builder){builder.buildMemory();builder.buildScreen();builder.buildAppearance();return builder.getiPhone();}
};
int main()
{Director director;//iphone14 miniiPhoneBuilder14Mini iphone14mini;std::unique_ptr<iPhone> mini = director.create(iphone14mini);std::cout << "iPhone 14 Mini" << std::endl;mini->showInfo();std::cout << std::endl;iPhoneBuilder14PRO iphone14PRO;std::unique_ptr<iPhone> pro = director.create(iphone14PRO);std::cout << "iPhone 14 Mini" << std::endl;pro->showInfo();std::cout << std::endl;
}

在这里插入图片描述

sunny和merry号生产

现在我们开始着手把路飞的海贼船桑尼号 和梅利号使用生成器模式键造出来。
1、一共需要三个生成器类,一共父类,两个子类;
2、父类可以是一个抽象类,提供的建造函数都是虚函数;
3、在两个生成器子类中,使用建造函数分别将桑尼号 和梅利号各个零部件造出来。
如果我们仔细分析,发现还需要解决另外一个问题,通过生成器得到了海贼船的各个零部件,这些零部件必须有一个载体,那就是海贼船对象。因此,还需要提供一个或多个海贼船类。
因为桑尼号 和梅利号这两艘的差别非常之巨大,所以我们定义两个海贼船类,代码如下:

#include <iostream>
#include <memory>
#include <map>
#include <vector>
#include <string>
using namespace std;/*******************************_两个船类(Sunny号和Merry号)_*************************************/
//产品1:Sunny号
class Sunnyship
{
public://添加零件void addParts(string name){m_parts.push_back(name);}void showParts(){for (const auto& item : m_parts){cout << item << " ";cout << endl;}}
private:vector<string> m_parts;
};
//产品2:Merry号
class Merryship
{
public://添加零件void assemble(string name,string parts){m_parts.insert(make_pair(name,parts));}void showParts(){for (const auto& item : m_parts){cout << item.first << ": "<<item.second << " ";cout << endl;}}
private:map<string,string> m_parts;
};
/**************************************************************************************************/
/*****************************************_生成器类_*********************************************************/
//抽象生成器类
class ShipBuilder
{
public:virtual void reset() = 0;virtual void buildBody() = 0;virtual void buildWeapon() = 0;virtual void buildEngine() = 0;virtual void buildInterior() = 0;virtual ~ShipBuilder() {}
};
//具体生成器类:Sunny号生成器
class SunnyBuilder :public ShipBuilder
{
public:SunnyBuilder(){reset();}~SunnyBuilder(){if (m_sunny != nullptr){delete m_sunny;}}void reset() override{m_sunny = new Sunnyship;}void buildBody(){m_sunny->addParts("神树亚当的树干");}void buildWeapon(){m_sunny->addParts("狮吼炮");}void buildEngine(){m_sunny->addParts("可乐驱动");}void buildInterior(){m_sunny->addParts("豪华精装修的内饰");}Sunnyship* getSunny(){Sunnyship* ship = m_sunny;m_sunny = nullptr;return ship;}private:Sunnyship* m_sunny = nullptr;
};
//具体生成器类:Merry号生成器
class MerryBuilder :public ShipBuilder
{
public:MerryBuilder(){reset();}~MerryBuilder(){if (m_merry != nullptr){delete m_merry;}}void reset() override{m_merry = new class Merryship;}void buildBody(){m_merry->assemble("船体","优质木材");}void buildWeapon(){m_merry->assemble("武器","四门大炮");}void buildEngine(){m_merry->assemble("动力","蒸汽机");}void buildInterior(){m_merry->assemble("内饰","精装修");}Merryship* getMerry(){Merryship* ship = m_merry;m_merry = nullptr;return ship;}private:Merryship* m_merry = nullptr;
};
/******************************************_导演类_***********************************************/
class Director
{
public:void setBuilder(ShipBuilder* builder){m_builder = builder;}void builderSimpleShip(){m_builder->buildBody();m_builder->buildEngine();}void builderStandShip(){builderSimpleShip();m_builder->buildWeapon();}void builderRegalShip(){builderStandShip();m_builder->buildInterior();}
private:ShipBuilder* m_builder = nullptr;
};
/*******************************_代码测试_**************************************************/
//建造Sunny号
void buildSunny()
{Director director;SunnyBuilder Sbuild;//简约型director.setBuilder(&Sbuild);director.builderSimpleShip();Sunnyship* Sship = Sbuild.getSunny();Sship->showParts();delete Sship;}
int main()
{buildSunny();
}

在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/95955.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

React Hooks —— ref hooks

什么是Hooks Hooks从语法上来说是一些函数。这些函数可以用于在函数组件中引入状态管理和生命周期方法。 React Hooks的优点 简洁 从语法上来说&#xff0c;写的代码少了上手非常简单 基于函数式编程理念&#xff0c;只需要掌握一些JavaScript基础知识与生命周期相关的知识不…

python:openpyxl 读取 Excel文件,显示在 wx.grid 表格中

pip install openpyxl openpyxl-3.1.2-py2.py3-none-any.whl (249 kB) et_xmlfile-1.1.0-py3-none-any.whl (4.7 kB) 摘要&#xff1a;A Python library to read/write Excel 2010 xlsx/xlsm files pip install wxpython4.2 wxPython-4.2.0-cp37-cp37m-win_amd64.whl (18.0 M…

微擎小程序获取不到头像和昵称解决方案

这是一个使用微擎小程序的代码示例&#xff0c;其中包含了获取用户头像和昵称的功能。以下是解决方案&#xff1a; 首先&#xff0c;在<button>标签上添加open-type"chooseAvatar"属性&#xff0c;并绑定bindchooseavatar事件&#xff1a; <button class&qu…

数据结构-快速排序-C语言实现

引言&#xff1a;快速排序作为一种非常经典且高效的排序算法&#xff0c;无论是工作还是面试中广泛用到&#xff0c;作为一种分治思想&#xff0c;需要熟悉递归思想。下面来讲讲快速排序的实现和改进。 老规矩&#xff0c;先用图解来理解一下&#xff1a;&#xff08;这里使用快…

MATLAB中syms函数使用

目录 语法 说明 示例 创建符号标量变量 创建符号标量变量的向量 创建符号标量变量矩阵 管理符号标量变量的假设 创建和评估符号函数 syms函数的作用是创建符号标量和函数&#xff0c;以及矩阵变量和函数。 语法 syms var1 ... varN syms var1 ... varN [n1 ... nM] …

指数分布优化器(EDO)(含MATLAB代码)

先做一个声明&#xff1a;文章是由我的个人公众号中的推送直接复制粘贴而来&#xff0c;因此对智能优化算法感兴趣的朋友&#xff0c;可关注我的个人公众号&#xff1a;启发式算法讨论。我会不定期在公众号里分享不同的智能优化算法&#xff0c;经典的&#xff0c;或者是近几年…

“秋天第一只大闸蟹”背后,看见京东一体化供应链

京东似乎正在从一个大闸蟹的物流服务商、销售商&#xff0c;转变为一个大闸蟹的“供货商”。 作者|斗斗 编辑|皮爷 出品|产业家 阳澄湖连续几天的降雨&#xff0c;使得通往蟹塘的路异常难走。 长期驻扎此地的京东相关负责人蹲在蟹塘边的小路上&#xff0c;指着蟹塘说道…

【RabbitMQ 实战】08 集群原理剖析

上一节&#xff0c;我们用docker-compose搭建了一个RabbitMQ集群&#xff0c;这一节我们来分析一下集群的原理 一、基础概念 1.1 元数据 前面我们有介绍到 RabbitMQ 内部有各种基础构件&#xff0c;包括队列、交换器、绑定、虚拟主机等&#xff0c;他们组成了 AMQP 协议消息…

QQ登录的具体流程

文章目录 网站授权QQ登录QQ登录的完整流程代码示例1. 添加依赖2. 配置文件3. 实现Service4. 创建Controller 网站授权QQ登录 首先需要去QQ互联申请应用填写网站的相关信息&#xff0c;以及回调地址&#xff0c;需要进行审核。申请流程暂时不说了&#xff0c;百度一下挺多申请失…

Cocos Creator3.8 项目实战(五)背景无限滚屏效果如何实现

在游戏中&#xff0c;我们经常会实现背景无限滚动的效果。那这些效果是怎么实现的呢&#xff1f; 原理很简单&#xff0c;就是使用多张背景图&#xff0c;每张图&#xff0c;每一帧都同时移动&#xff0c;当图移出屏幕外时&#xff0c;将其位置设置到下一张图的初始位置&#x…

23云计算全国职业技能大赛容器云-容器编排

erp 2.2.1 容器化部署 MariaDB [0.5 分]2.2.2 容器化部署 Redis [0.5 分]2.2.3 容器化部署 Nginx [0.5 分]2.2.4 容器化部署 ERP[0.5 分]2.2.5 编排部署 ERP管理系统[1 分] 2.2.1 容器化部署 MariaDB [0.5 分] 编写 Dockerfile 文件构建 mysql 镜像&#xff0c;要求基于 centos…

【AI视野·今日NLP 自然语言处理论文速览 第四十八期】Thu, 5 Oct 2023

AI视野今日CS.NLP 自然语言处理论文速览 Thu, 5 Oct 2023 Totally 50 papers &#x1f449;上期速览✈更多精彩请移步主页 Daily Computation and Language Papers Retrieval meets Long Context Large Language Models Authors Peng Xu, Wei Ping, Xianchao Wu, Lawrence McA…

[架构之路-231]:计算机硬件与体系结构 - 性能评估汇总,性能优化加速比

目录 一、计算机体系结构 二、计算机性能评估 2.1 分类方法1 2.2 分类方法2 三、常见的专项性能测试工具 3.1 浮点运算性能&#xff08;FLOPS&#xff09; 3.2 综合理论性能法 3.3 历史基准测试&#xff08;跑分软件&#xff09;&#xff1a;通过运行典型的综合性的程序…

反爬虫机制与反爬虫技术(一)

反爬虫机制与反爬虫技术一 1、网络爬虫的法律与道德问题2、反爬虫机制与反爬虫技术2.1、User-Agent伪装2.2、代理IP2.3、请求频率控制2.4、动态页面处理2.5、验证码识别3、反爬虫案例:豆瓣电影Top250爬取3.1、爬取目标3.2、库(模块)简介3.3、翻页分析3.4、发送请求3.5、提取…

【VUE·疑难问题】定义 table 中每行的高度(使用 element-UI)

一、如何定义 table 中每一行的 height &#xff1f; 1.table例子 <!-- 二、table --><div style"overflow: hidden;display: block;height: 68vh;width: 100%;"><el-table stripe show-header style"width: 100%" :data"tableData&q…

mysql面试题20:有哪些合适的分布式主键方案

该文章专注于面试,面试只要回答关键点即可,不需要对框架有非常深入的回答,如果你想应付面试,是足够了,抓住关键点 面试官:有哪些合适的分布式主键方案? UUID:UUID通常是由一个二进制的128位整数表示,可以保证全局的唯一性。在Java中,可以通过UUID类生成一个UUID。例…

浏览器性能优化

IIFE惰性函数 有一些函数在运行时需要进行一些判断&#xff0c;但是这个判断只需要执行一次&#xff0c;代码一旦运行判断结果就不会改变&#xff0c;这样的函数称为惰性函数&#xff0c;可以使用下面的手段来进行优化 // 优化前&#xff0c;每次调用都需要进行一次判断 functi…

Hadoop伪分布式环境搭建

什么是Hadoop伪分布式集群&#xff1f; Hadoop 伪分布式集群是一种在单个节点上模拟分布式环境的配置&#xff0c;用于学习、开发和测试 Hadoop 的功能和特性。它提供了一个简化的方式来体验和熟悉 Hadoop 的各个组件&#xff0c;而无需配置和管理一个真正的多节点集群。 在 Ha…

定量活性关系(QSAR)是什么?定量结构-性质关系(QSPR)是什么?

定量活性关系&#xff08;QSAR&#xff09;是什么&#xff1f; 定量活性关系&#xff08;QSAR&#xff0c;Quantitative Structure-Activity Relationship&#xff09;分析是指利用理论计算和统计分析工具来研究系列化合物结构&#xff08;包括二维分子结构、三维分子结构和电…

C++ 学习系列 -- std::list

一 std::list 介绍 list 是 c 中的序列式容器&#xff0c;其实现是双向链表&#xff0c;每个元素都有两个指针&#xff0c;分别指向前一个节点与后一个节点 链表与数组都是计算机常用的内存数据结构&#xff0c;与数组连续内存空间不一样的地方在于&#xff0c;链表的空间是不…