创建型模式 | 工厂模式

文章目录

  • 一、简单工厂
    • 1.1、原理
    • 1.2、核心角色
    • 1.3、UML类图
    • 1.4、代码实现
    • 1.5、总结
  • 二、工厂模式
    • 2.1、原理
    • 2.2、关键角色
    • 2.3、代码实现
    • 2.4、总结
  • 三、抽象工厂模式
    • 3.1、原理
    • 3.2、关键角色
    • 3.3、UML类图
    • 3.4、工厂模式与抽象工厂模式的区别

前言

工厂模式是最常用的设计模式之一,它提供了一种创建对象的最佳方式,在创建对象的时候,不会对客户端暴露创建逻辑,并且通过使用一个共同的接口来创建新的对象。工厂模式有三种,分别是简单工厂、工厂模式,抽象工厂

一、简单工厂

1.1、原理

通过传⼊相关的类型来返回相应的类对象,简单工厂模式看为工厂方法模式的一种特例。

1.2、核心角色

  • 简单工厂(SimpleFactory):根据类型创建类对象
  • 抽象产品(IProduct):产品接口,描述所有实例对象的公共接口
  • 具体产品(ConcreteProduct):实现产品接口

1.3、UML类图

下面以生成手机的代码为例,介绍简单工厂模式,UML类图如下:

在这里插入图片描述

1.4、代码实现

代码实现,如下:

#include <iostream>
using namespace std;// 手机(抽象接口)
class IPhone {
public:virtual void Describe() = 0;
};// 华为手机(具体产品)
class HuaweiPhone : public IPhone {
public:void Describe() {cout << "华为手机" << endl;}
};// 苹果手机(具体产品)
class ApplePhone : public IPhone {
public:void Describe() {cout << "苹果手机" << endl;}
};// 简单工厂
class PhoneFactory {
public:IPhone* Produce(string type) {IPhone *pPhone = nullptr;if (type == "Huawei") {pPhone = new HuaweiPhone;} else if (type == "Apple") {pPhone = new ApplePhone;}return pPhone;}
};int main()
{// 简单工厂PhoneFactory factory;IPhone *pHuaweiPhone = factory.Produce("Huawei");IPhone *pApplePhone = factory.Produce("Apple");pHuaweiPhone->Describe();pApplePhone->Describe();return 0;
}

1.5、总结

简单工厂模式优点与缺点,如下:

优点:

  • 实现简单
  • 实现了对象创建与业务逻辑的分离

缺点:

  • 可扩展性差,如果新增手机产品,就需要修改PhoneFactory::Produce方法,违反了开放封闭原则

二、工厂模式

2.1、原理

定义创建对象抽象工厂,具体工厂负责实现抽象工厂接口,创建对应类型的对象

2.2、关键角色

  • 抽象工厂:定义了创建抽象产品的抽象工厂
  • 具体工厂:实现抽象工厂接口的具体工厂类,负责生产具体的产品
  • 抽象产品:产品接口,描述所有实例对象的公共接口
  • 具体产品:实现产品接口

2.3、代码实现

#include <iostream>
using namespace std;// 手机(抽象接口)
class IPhone {
public:virtual void Describe() = 0;
};// 华为手机(具体产品)
class HuaweiPhone : public IPhone {
public:void Describe() {cout << "华为手机" << endl;}
};// 苹果手机(具体产品)
class ApplePhone : public IPhone {
public:void Describe() {cout << "苹果手机" << endl;}
};// 抽象工厂
class IFactory {
public:virtual IPhone* Produce() = 0;
};// 具体工厂(生产华为手机)
class HuaweiPhoneFactory : public IFactory {
public:IPhone* Produce() {return new HuaweiPhone;}
};// 具体工厂(生产苹果手机)
class ApplePhoneFactory : public IFactory {
public:IPhone* Produce() {return new ApplePhone;}
};int main()
{// 工厂对象HuaweiPhoneFactory huaweiFactory;ApplePhoneFactory appleFactory;IPhone *pHuaweiPhone = huaweiFactory.Produce();IPhone *pApplePhone = appleFactory.Produce();pHuaweiPhone->Describe();pApplePhone->Describe();return 0;
}

2.4、总结

工厂模式优点与缺点,如下:

优点:

  • 解决了简单工厂模式可扩展性差的问题,如果新增手机产品,新增一个产品类及对应的工厂类就可以,不会修改原有的代码,符合开放封闭原则

缺点:

  • 随着产品的增多,类的个数容易过多,增加复杂度
  • 具体工厂只能生产出一种产品(可以用抽象工厂模式解决)

三、抽象工厂模式

3.1、原理

抽象工厂模式在工厂方法模式的基础上进行进一步抽象。设想下面这种场景:在手机的基础上新增了Pad,要创建华为Phone华为Pad苹果Phone苹果Pad等产品,如果使用工厂模式,就要新增四个工厂类,使用工厂方法模式,创建了很多具体工厂类,而没有利用产品的商品族的概念。

抽象工厂模式是用于解决一类产品的创建问题(在上述场景中,可以把华为Phone华为Pad苹果Phone苹果Pad归纳为PhonePad这两类商品)

3.2、关键角色

抽象工厂模式与工厂模式的关键角色类似,有差异的地方在于抽象工厂类,如下:

  • 抽象工厂类:定义一组接口,用于创建多类产品;工厂方法的抽象工厂类,只定义了创建一类产品的接口

3.3、UML类图

使用抽象工厂类解决工厂方法遇到的两个问题,一是:只能生产一类产品的问题;二是:增加产品导致产品工厂类的个数容易过多的问题(解决新增Pad产品的问题,如果使用抽象工厂方法需要新增两个工厂类,而使用工厂方法需要四个工厂类),UML类图如下:

在这里插入图片描述

3.4、工厂模式与抽象工厂模式的区别

工厂模式主要解决一类产品的创建问题,抽象工厂模式主要是来解决多类(产品簇)产品创建问题。具体差异体现在抽象工厂角色上,工厂模式提供一个接口,创建一类产品;抽象工厂提供多个接口,可以创建多类产品。

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

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

相关文章

C#用正则表达式获取字符串中汉字的数量

目录 一、关于字符串和判断其组成常识 二、用正则表达式获取字符串中汉字的数量 1.字符是否为汉字的正则表达式 2.实例 3.生成结果 三、相关知识点 1.Regex.IsMatch 方法 一、关于字符串和判断其组成常识 字符串中可以包括数字、字母、汉字或者其他字符。使用Char类型的…

pyhon中File对象的属性及如何读取DBF文件

pyhon中File对象的属性 一个文件被打开后&#xff0c;你有一个file对象&#xff0c;你可以得到有关该文件的各种信息。 以下是和file对象相关的所有属性的列表&#xff1a; 如下实例&#xff1a; #!/usr/bin/python# 打开一个文件 fo open("foo.txt", "wb&quo…

HarmonyOS自定义组件生命周期函数介绍

aboutToAppear 在创建自定义组件的新实例后&#xff0c;在执行其build()函数之前执行。允许在aboutToAppear函数中改变状态变量&#xff0c;更改将在后续执行build()函数中生效。 aboutToDisappear 在自定义组件析构销毁之前执行。不允许在aboutToDisappear函数中改变状态变…

【K8S 存储卷】K8S的存储卷+PV/PVC

目录 一、K8S的存储卷 1、概念&#xff1a; 2、挂载的方式&#xff1a; 2.1、emptyDir&#xff1a; 2.2、hostPath&#xff1a; 2.3、NFS共享存储&#xff1a; 二、PV和PVC&#xff1a; 1、概念 2、请求方式 3、静态请求流程图&#xff1a; 4、PV和PVC的生命周期 5、…

scratch考试“画图”相关考点一网打尽

最近2023年12月17日举行的第15届蓝桥STEMA测评Scratch编程初/中级组编程第3题—六花阵图 在讲解这个题目,可以延申scratch所有的基础图形,学会这篇,碰到关于“图形”类题目基本上都可以搞定 六花阵图 编程实现: 六花阵图。 注意:六花阵图必须使用画笔绘制,画面中不允…

Vue 自定义仿word表单录入之日期输入组件

因项目需要&#xff0c;要实现仿word方式录入数据&#xff0c;要实现鼠标经过时才显示编辑组件&#xff0c;预览及离开后则显示具体的文字。 鼠标经过时显示 正常显示及离开时显示 组件代码 <template ><div class"paper-input flex flex-col border-box "…

从0开始python学习-47.pytest框架之解决Template替换无法进行二次处理的问题之热加载

问题&#xff1a;当参数为动态参数时&#xff0c;Template替换无法进行二次处理 解决方案&#xff1a;通过热加载来进行替换 热加载原理&#xff1a;在代码运行的过程中动态的调用python中的方法达到获得动态参数 可以进行热加载的情况&#xff1a;yaml文件&#xff0c;随机…

金和OA jc6 GetAttOut SQL注入漏洞复现

0x01 产品简介 金和OA协同办公管理系统软件(简称金和OA),本着简单、适用、高效的原则,贴合企事业单位的实际需求,实行通用化、标准化、智能化、人性化的产品设计,充分体现企事业单位规范管理、提高办公效率的核心思想,为用户提供一整套标准的办公自动化解决方案,以帮助…

原型模式

为什么要使用原型模式 不用重新初始化对象&#xff0c;而是动态地获得对象运行时的状态。适用于当创建对象的成本较高时&#xff0c;如需进行复杂的数据库操作或复杂计算才能获得初始数据。 优点是可以隐藏对象创建的细节&#xff0c;减少重复的初始化代码&#xff1b;可以在…

小程序基础学习(事件处理)

概述&#xff1a;点击某一个标题&#xff0c;使标题选中增加不同颜色。 <!--pages/four/four.wxml--> <navigation-bar title"牧原" back"{{false}}" color"black" background"#FFF"></navigation-bar> <view c…

Docker的介绍及安装基本操作命令

前言 Docker 是一个开源的应用容器引擎&#xff0c;基于 Go 语言 并遵从 Apache2.0 协议开源。 Docker 可以让开发者打包他们的应用以及依赖包到一个轻量级、可移植的容器中&#xff0c;然后发布到任何流行的 Linux 机器上&#xff0c;也可以实现虚拟化。 容器是完全使用沙箱…

【每日一题】2696. 删除子串后的字符串最小长度-2024.1.10

题目&#xff1a; 2696. 删除子串后的字符串最小长度 给你一个仅由 大写 英文字符组成的字符串 s 。 你可以对此字符串执行一些操作&#xff0c;在每一步操作中&#xff0c;你可以从 s 中删除 任一个 "AB" 或 "CD" 子字符串。 通过执行操作&#xff0c…