工厂模式—
GOF23 种正式设计模式,是工厂方法的「终极升级版」,也是 C++ 中解耦性最强的工厂模式;核心: 一个抽象工厂接口,用于创建一系列相关产品族,而无需制定他们的类两个概念产品等级结构: 同一种产品的【基类+子类】,比如人形基类+榆树人形机器人+云深处机器人是一个产品等级,四足基类+榆树机器狗+云深处机器狗是一个产品等级。产品族: 同一个品牌/同一家工厂生产的,配套使用的不同产品,比如【榆树机器人
工厂模式
三种类型
-
简单工厂模式
-
工厂方法模式
-
抽象工厂模式
🌰
所有工厂模式核心
核心: 将对象new的过程,改为向工厂索取
-
业务层:负责
使用对象,用不写new -
工厂层:负责
创建对象,所有实例化对象逻辑都在这 -
优点:开闭原则1 ,里氏替换原则2
-
所有产品类继承自同一个基类、纯虚函数,所有工厂类继承同一个工厂基类/纯虚函数,全程使用多态
[footnotes] :(新增产品,只改工厂,不该业务)
[2] 子类可以完全实现父类
简单工厂模式
不是 GOF23 种正式设计模式,是工厂模式的基础,也叫「静态工厂模式」,是 C++ 最常用的入门工厂;
核心:一个工厂类 + 一个判断逻辑,工厂类里写一个「静态创建方法」,通过传入的字符串 / 枚举参数,用
if/switch判断,创建并返回不同的产品对象;所有产品都继承同一个基类,返回值是基类指针 / 引用(C++ 多态的核心体现)。
☑️特征
一个万能工厂,生产所有类,靠参数决定生产什么
🌰
#include <iostream>
#include <string>品的 while 循环里 int num = 0; 写在循环体内 → 每次循环都重置,死循环!把 num 提出循环外或干脆用 for
using namespace std;
// =======第一步:定义【产品基类】- 所有机器人的统一规范(抽象类) =====
class R{
public:
//纯虚函数,all robot must 实现生成机器人这个行为
virtual void makeR() = 0;
//析构虚函数,C++继承必须写,防止内存泄漏
virtual ~R(){}
};
// ======第二步:定义【具体惨产品子类】- 继承产品基类 ====
// 榆树机器人产品
class YS : public R{
void makeR() override{//重写基类纯虚函数
bool ys = 0;
int num = 0;
while(!ys){
num++;
if(num == 520){
ys = 1;
num = 0;
}
}
}
};
// 云深处机器人产品
class YSC : public R{
void makeR() override{//重写基类纯虚函数
bool ysc = 0;
int num = 0;
while(!ysc){
num++;
if(num == 520){
ysc = 1;
num = 0;
}
}
}
};
// ====== 第三步: 核心 - 唯一的【简单工厂类】 ====
class RFty{
public:
//静态创建方法:传参数,返回产品基类指针
static R* buildR(string name){
R* r = nullptr;
//根据传入参数,创建对应产品
if(name == "宇"){
r = new YS;
}
else if(name == "云"){
r = new YSC;
}
return r;
}
};
// ====== 测试: 业务层代码(只使用不创建) ====
int main(){
//要榆树机器人,只要给工厂发送索求,拿到基类指针
R* ys = RFty::buildR("宇");
ys->makeR(); //多态调用
//要云生出机器人,只要给工厂发送索求,拿到基类指针
R* ysc = RFty::buildR("云");
ysc->makeR(); //多态调用
//手动释放堆内存
delete ys;
delete ysc;
ys = nullptr;
ysc = nullptr;
return 0;
}
✅极简,易用,代码量少
🚨违反开闭原则,如增加纵情机器人,必须修改工厂类的if判断逻辑,工厂会越来越臃肿
工厂方法模式(Factory Method Pattern)
GOF23 种正式设计模式,是简单工厂的「升级版」,解决了简单工厂违反开闭原则的核心痛点;
核心 : 定义抽象工厂类(纯虚类),只声明创建产品的纯虚方法,不实现具体逻辑;每个具体产品,都对应一个专属具体工厂子类
逻辑创建时延迟到具体工厂子类中实现,不再if/swich判断;
C++核心:抽象工厂的纯虚方法返回产品基类指针,具体实现工厂重写该方法,返回对应产品指针,全程多态
特征 一个产品一个专属工厂,各管各的,无万能工厂
🌰
#include <iostream>
using namespace std;
// ====== 第一步:产品【产品基类】 - 所有机器人统一规范 ====
class R{
public:
virtual void makeR() = 0;
virtual ~R(){}
};
// ======具体:榆树 ====
class ys : public R{
void makeR() override{
int num = 0;
bool ys = false;
while(!ys){
num++;
if(num == 77){
ys = true;
num = 0;
}
}
}
};
// ======具体:云深处 ====
class ysc : public R{
void makeR() override{
int num = 0;
bool ysc = false;
while(!ysc){
num++;
if(num == 77){
ysc = true;
num = 0;
}
}
}
};
// ====== 第二步: 核心1 -定义【抽象工厂类】纯虚函数 ====
//只规定每个厂有找机器人能力,不写具体实现
class AbstractFty{
public:
virtual R* buildR() = 0; //纯虚函数创建方法
virtual ~AbstractFty(){}
};
// ====== 第三步 核心2 -每个产品对应一个厂【具体】 ====
//榆树厂:只做机器人专属工厂
class ysfty : public AbstractFty{
public:
R* buildR() override{
return new ys;
}
};
//云深处厂:只做机器人专属工厂
class yscfty : public AbstractFty{
public:
R* buildR() override{
return new ysc;
}
};
// ====== 测试: 业务层代码 ====
int main(){
//需求1 要榆树机器人 -> 创建榆树厂,调用厂的实现方法
AbstractFty* YsFty = new ysfty;
R* ysr = YsFty->buildR();
ysr->makeR();
//需求1 要云深处机器人 -> 创建云深处厂,调用厂的实现方法
AbstractFty* YscFty = new yscfty;
R* yscr = YscFty->buildR();
yscr->makeR();
delete ysr;
delete yscr;
delete YsFty;
delete YscFty;
return 0;
}
✅完美遵循开闭原则!如果要增加【纵情机器人】,只需两件事
-
新增 zq类,继承R并重写makeR();
-
新增zqfty类, 继承AbstractFty并重写buildR();
🚨类数量翻倍,产品越多。类越多,越复杂。而且只能生产单一产品,不能生产【成套产品】(比如人形机器人和四足机器人)
抽象工厂(Abstract Factory Pattern)
GOF23 种正式设计模式,是工厂方法的「终极升级版」,也是 C++ 中解耦性最强的工厂模式;
核心: 一个抽象工厂接口,用于创建一系列相关产品族,而无需制定他们的类
两个概念
-
产品等级结构: 同一种产品的【基类+子类】,比如人形基类+榆树人形机器人+云深处机器人是一个产品等级,四足基类+榆树机器狗+云深处机器狗是一个产品等级。
-
产品族: 同一个品牌/同一家工厂生产的,配套使用的不同产品,比如【榆树机器人加榆树机器狗】是榆树产品族,...
特征 一个工厂生产一套产品,不生产单一产品
🌰
#include <iostream>
using namespace std;
// ======= 第一步: 定义 【两个产品等级结构】 ====
// 产品等级1: 人形产品的基类(抽象)
class R{
public:
virtual void makeR() = 0;
virtual ~R(){}
};
// 榆树人形 (属于榆树产品族)
class ysr : public R{
void makeR() override{
int num = 0;
bool ysr = false;
while(!ysr){
num++;
if(num == 99){
num = 0;
ysr = true;
}
}
}
};
// 云深处人形 (属于云深处产品族)
class yscr : public R{
void makeR() override{
int num = 0;
bool yscr = false;
while(!yscr){
num++;
if(num == 99){
num = 0;
yscr = true;
}
}
}
};
// 产品等级2: 机器狗的基类(抽象)
class D{
public:
virtual void makeD() = 0;
virtual ~D(){}
};
// 榆树狗 (属于榆树产品族)
class ysd : public D{
void makeD() override{
int num = 0;
bool ysd = false;
while(!ysd){
num++;
if(num == 99){
num = 0;
ysd = true;
}
}
}
};
// 云深处狗 (属于云深处产品族)
class yscd : public D{
void makeD() override{
int num = 0;
bool yscd = false;
while(!yscd){
num++;
if(num == 99){
num = 0;
yscd = true;
}
}
}
};
// ====== 核心 - 定义【抽象工厂类】 ====
//抽象工厂:规定【产品族】的所有产品创建方法
//要求所有厂都能生产人形和机器狗这一套产品
class AbsFty{
public:
virtual R* buildR() = 0;
virtual D* buildD() = 0;
virtual ~AbsFty(){}
};
// ====== 定义:【具体工厂类】 - 一个工厂对应一个产品族 =====
//榆树工厂 只生产所有榆树产品 人形 + 机器狗
class ysfty : public AbsFty{
public:
R* buildR() override{
return new ysr;
}
D* buildD() override{
return new ysd;
}
};
//云深处工厂 只生产所有云深处产品 人形 + 机器狗
class yscfty : public AbsFty{
public:
R* buildR() override{
return new yscr;
}
D* buildD() override{
return new yscd;
}
};
// =======测试 业务代码 ===
int main(){
//需求1。 我要一套榆树产品, -> 创建榆树工厂
AbsFty* Ysfty = new ysfty;
R* Ys = Ysfty->buildR();
D* Ysd = Ysfty->buildD();
Ys->makeR();
Ysd->makeD();
//需求2。 我要一套云深处产品, -> 创建云深处工厂
AbsFty* Yscfty = new yscfty;
R* Ysc = Yscfty->buildR();
D* Yscd = Yscfty->buildD();
Ysc->makeR();
Yscd->makeD();
delete Ys; delete Ysd; delete Ysfty;
delete Ysc; delete Yscd; delete Yscfty;
return 0;
}
DAMO开发者矩阵,由阿里巴巴达摩院和中国互联网协会联合发起,致力于探讨最前沿的技术趋势与应用成果,搭建高质量的交流与分享平台,推动技术创新与产业应用链接,围绕“人工智能与新型计算”构建开放共享的开发者生态。
更多推荐

所有评论(0)