【设计模式】创建型设计模式之 工厂模式

一、介绍

工厂模式可以分为 3 个小类

  1. 简单工厂模式
  2. 工厂方法模式
  3. 抽象工厂模式

工厂模式的工厂类,并不一定以 Factory 结尾,例如 DataFormat、Calender 他们都是工厂类,通过静态方法来创建实例。

除此之外,创建对象的方法名称一般是 create+类名,但是也有其他的命名方式例如 getInstance()、createInstance() createInstance() ,甚至是 valueOf 也是工厂的方法例如 String 的 valueOf()方法。


二、简单工厂模式

介绍

image.png

  1. 将创建对象的函数,从代码中剥离并且将其放到一个独立的类中。让这个类只负责对象的创建。那这个类就是简单工厂模式的工厂类。
  2. 虽然大部分的工厂模式的结尾都是 Factory,但是不是必须的,例如 Java 中的 DateFormat、Calender 尽管没有以 Factory 但是他们也是工厂类。甚至 String.valueOf 也是工厂类。

自定义案例代码

// 定义 Shape 接口
interface Shape {void draw();
}// 具体形状类:圆形
class Circle implements Shape {@Overridepublic void draw() {System.out.println("Inside Circle::draw() method.");}
}// 具体形状类:矩形
class Rectangle implements Shape {@Overridepublic void draw() {System.out.println("Inside Rectangle::draw() method.");}
}// 简单工厂类,用于创建形状对象
class ShapeFactory {// 使用 getShape 方法获取形状类型的对象public static Shape getShape(String shapeType) {if (shapeType == null) {return null;} else if (shapeType.equalsIgnoreCase("CIRCLE")) {return new Circle();} else if (shapeType.equalsIgnoreCase("RECTANGLE")) {return new Rectangle();}return null;}
}// 客户端代码
public class SimpleFactoryPatternDemo {public static void main(String[] args) {// 获取形状类型的对象Shape shape1 = ShapeFactory.getShape("CIRCLE");// 调用 Circle 的 draw 方法shape1.draw();Shape shape2 = ShapeFactory.getShape("RECTANGLE");// 调用 Rectangle 的 draw 方法shape2.draw();// 请求一个不支持的形状类型Shape shape3 = ShapeFactory.getShape("SQUARE");if (shape3 != null) {shape3.draw();} else {System.out.println("Shape not supported.");}}
}

第二类简单工厂

如果将简单工厂模式和类似的单例模式组合起来,那么可以称之为第二类简单工厂模式

public class ReleConfigParseFactory{private static final Map<String,RuleConfigParse> rulesMap=new HashMap<>();static{rulesMap.put(XXXX)}public static getParse(String name){return relesMap.get(name);}
}



三、工厂方法模式

  1. 简单工厂模式如果要新增产品类型则需要在工厂类中新增 不够符合开闭原则
  2. 工厂方法模式 对于新增一个具体的产品来说,只需要新增一个工厂类更符合开闭原则。
  3. 在业务中创建工厂类仍然负责,所以可以结合简单工厂。对于具体的 FactoryABC 再创建一个简单工厂也就是工厂的工厂。这样新增工厂类后,只需要在工厂的工厂中添加该工厂而不需要大量的改动。

缺点:

  1. 工厂类只包含一个创建代码,功能单薄有点过度设计。如果代码足够简单,应该使用简单工厂模式。



四、抽象工厂模式


如果具体需要创建的对象包含多种分类,那么实用工厂方法模式可能会产生大量的工厂类。
例如上图,包含两种产品 Computer 和 Phone ,同事包含两个厂商 小米和苹果,如果使用工厂方法则会产生四个工厂。
引入抽象工厂模式后,AppleFactory 和 MiFactory 每个工厂负责多种类型的产品可以有效减少对应工厂的个数。



五、总结

使用工厂模式的场景

场景 1:代码中存在根据不同条件创建不同对象的代码,可以考虑使用工厂模式将这一大段代码进行抽离。如果每个对象的创建都比较简单那么就使用简单工厂模式,如果对象的创建过程比较负责责使用工厂方法模式将每个对象的创建过程封装到各自的工厂类中。
**场景 2:**一个类的对象创建比较复杂,例如涉及其他的对象,复杂的初始化逻辑等。也可以考虑使用工厂模式,将对象创建的过程封装到工厂模式中。
工厂模式作用总结:

可以根据下面四条规则判断是否使用工厂模式

  1. 封装变化 利用工厂模式封装创建逻辑,创建逻辑的变更对调用者透明。
  2. 代码复用 避免业务中创建对象的代码散落各处,避免重复编写。
  3. 隔离复杂性:封装复杂的创建逻辑,让使用者无需关注具体的创建细节。
  4. 控制复杂度:将创建逻辑与使用逻辑分离,简化代码。

开发中常见的工厂模式案例

  1. DateFormat、Calendar 类
  2. 日志工厂 LoggerFactory 经常使用工厂模式来创建日志记录器(Logger)实例。开发者可以通过工厂方法请求一个日志记录器,而不需要知道具体实现细节。这样可以在不修改应用程序代码的情况下,灵活切换日志框架。
  3. Spring 这种 DI 框架,例如 BeanFactory 管理着对象的声明周期,也作为对象的创建工厂

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

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

相关文章

VBA即用型代码手册:删除重复行Delete Duplicate Rows

我给VBA下的定义&#xff1a;VBA是个人小型自动化处理的有效工具。可以大大提高自己的劳动效率&#xff0c;而且可以提高数据的准确性。我这里专注VBA,将我多年的经验汇集在VBA系列九套教程中。 作为我的学员要利用我的积木编程思想&#xff0c;积木编程最重要的是积木如何搭建…

电商项目-day01

文章目录 虚拟机的导入 虚拟机的导入 现根据镜像文件进行导入

streamlit:如何快速构建一个应用,不会前端也能写出好看的界面

通过本文你可以了解到&#xff1a; 如何安装streamlit&#xff0c;运行起来第一个demo熟悉streamlit的基本语法&#xff0c;常用的一些组件使用streamlit库构建应用 大模型学习参考&#xff1a; 大模型学习资料整理&#xff1a;如何从0到1学习大模型&#xff0c;搭建个人或企业…

(二)深度学习基础练习题(54道选择题)

本文整理了深度学习基础知识相关的练习题&#xff0c;共54道&#xff0c;适用于想巩固深度学习基础的同学。来源&#xff1a;如荷学数据科学题库&#xff08;技术专项-深度学习&#xff09;。 1&#xff09; 2&#xff09; 3&#xff09; 4&#xff09; 5&#xff09; 6&#…

音程与和弦 音程协和度

2个音符之间的音程计算 1234567&#xff0c;1到7的音程是7度&#xff0c;音程是计算总长度&#xff0c;看音级的个数。 Cubase中的音程计算 下面一个是4度&#xff0c;一个是3度&#xff0c;格子中深色的行就是黑键行。 根据半音数量来确定对应音程的专业术语叫法 旋律音程、…

用咖啡来理解springboot3的自动配置机制

大家好&#xff0c;这里是教授.F 目录 前提知识&#xff1a; 场景引入&#xff1a; 1.Starter依赖&#xff1a; 2.默认配置&#xff1a; 3.自定义配置&#xff1a; 4.条件化配置&#xff1a; 5.自动装配&#xff1a; 具体过程&#xff1a; 扫包路径的配置&#xff1a; 配置…

解锁ChatGPT:从GPT-2实践入手解密ChatGPT

⭐️我叫忆_恒心&#xff0c;一名喜欢书写博客的研究生&#x1f468;‍&#x1f393;。 如果觉得本文能帮到您&#xff0c;麻烦点个赞&#x1f44d;呗&#xff01; 近期会不断在专栏里进行更新讲解博客~~~ 有什么问题的小伙伴 欢迎留言提问欧&#xff0c;喜欢的小伙伴给个三连支…

【深度学习】—— 神经网络介绍

神经网络介绍 本系列主要是吴恩达深度学习系列视频的笔记&#xff0c;传送门&#xff1a;https://www.coursera.org/deeplearning-ai 目录 神经网络介绍神经网络的应用深度学习兴起的原因 神经网络&#xff0c;全称人工神经网络&#xff08;Artificial Neural Network&#xf…

python生成免费的ssl证书

测试SSL证书不需要验证域名权限 执行 pip install cryptography from cryptography import x509 from cryptography.x509.oid import NameOID from cryptography.hazmat.primitives import hashes, serialization from cryptography.hazmat.primitives.asymmetric import r…

私有化AI搜索引擎FreeAskInternet

什么是 FreeAskInternet FreeAskInternet 是一个完全免费、私有且本地运行的搜索聚合器&#xff0c;并使用 LLM 生成答案&#xff0c;无需 GPU。用户可以提出问题&#xff0c;系统将使用 searxng 进行多引擎搜索&#xff0c;并将搜索结果合并到ChatGPT3.5 LLM 中&#xff0c;并…

Python私教张大鹏 Vue3整合AntDesignVue之Breadcrumb 面包屑

显示当前页面在系统层级结构中的位置&#xff0c;并能向上返回。 何时使用 当系统拥有超过两级以上的层级结构时&#xff1b; 当需要告知用户『你在哪里』时&#xff1b; 当需要向上导航的功能时。 案例&#xff1a;面包屑导航基本使用 核心代码&#xff1a; <template…

【Linux文件篇】系统文件、文件描述符与重定向的实用指南

W...Y的主页 &#x1f60a; 代码仓库分享&#x1f495; 前言&#xff1a;相信大家对文件都不会太陌生、也不会太熟悉。在没有学习Linux操作系统时&#xff0c;我们在学习C或C时都学过如何去创建、打开、读写等待文件的操作&#xff0c;知道一些语言级别的一些接口与函数。但…

【Anaconda】 anaconda常用命令总结

【Anaconda】 anaconda常用命令总结 一、创建虚拟环境二、激活/使用/进入某个虚拟环境三、退出当前环境四、复制某个虚拟环境五、删除某个环境六、查看当前所有环境七、查看当前虚拟环境下的所有安装包八、安装或卸载包(进入虚拟环境之后&#xff09;九、分享虚拟环境十、源服务…

leetcode刷题记录34-100297. 找到连续赢 K 场比赛的第一位玩家

问题描述 有 n 位玩家在进行比赛&#xff0c;玩家编号依次为 0 到 n - 1 。 给你一个长度为 n 的整数数组 skills 和一个 正 整数 k &#xff0c;其中 skills[i] 是第 i 位玩家的技能等级。skills 中所有整数 互不相同 。 所有玩家从编号 0 到 n - 1 排成一列。 比赛进行方式如…

实体商铺私域流量打造策略:从引流到转化的全链路解析

在数字化时代&#xff0c;实体商铺面临着前所未有的挑战与机遇。随着线上购物的兴起&#xff0c;传统商铺如何吸引并留住顾客&#xff0c;成为了每个实体店家必须面对的问题。私域流量的打造&#xff0c;正是解决这一问题的关键所在。本文将从引流、留存、转化三个方面&#xf…

Java基础教程 - 15 进阶部分

更好的阅读体验&#xff1a;点这里 &#xff08; www.doubibiji.com &#xff09; 15 进阶部分 网络编程、注解、反射、泛型、新特性等&#xff0c;见高级部分。 继续学习 Java进阶教程

冯喜运:6.10周一黄金原油行情趋势分析及独家操作建议

【黄金消息面分析】&#xff1a;上周全球金融市场惊现戏剧性大逆转&#xff0c;美国多项经济数据证实劳动力市场降温&#xff0c;9月降息重返视野令全球风险情绪几乎陷入狂热状态&#xff0c;全球股市接连创新高&#xff0c;但上周五意外“爆表”的非农令市场惊现大逆转&#x…

基于pytorch_lightning测试resnet18不同激活方式在CIFAR10数据集上的精度

基于pytorch_lightning测试resnet18不同激活方式在CIFAR10数据集上的精度 一.曲线1.train_acc2.val_acc3.train_loss4.lr 二.代码 本文介绍了如何基于pytorch_lightning测试resnet18不同激活方式在CIFAR10数据集上的精度 特别说明: 1.NoActive:没有任何激活函数 2.SparseActiva…

Spring (49)OpenFeign

OpenFeign是Spring Cloud在Feign的基础上进行了增强&#xff0c;使其更易于与Spring Boot应用集成。它提供了一种声明式的方法来调用HTTP服务&#xff0c;从而简化了服务间调用的开发。下面我们将通过源码解析和代码演示来深入理解OpenFeign的工作原理及其使用方法。 1. 核心概…

调研管理系统的设计

管理员账户功能包括&#xff1a;系统首页&#xff0c;个人中心&#xff0c;管理员管理&#xff0c;基础数据管理&#xff0c;教师类型管理&#xff0c;课程类型管理&#xff0c;公告类型管理 前台账户功能包括&#xff1a;系统首页&#xff0c;个人中心&#xff0c;论坛&#…