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

结合简单工厂和工厂方法模式:实现灵活的对象创建

前言

在软件开发过程中,创建对象的方式直接影响代码的灵活性和可维护性。设计模式提供了一种解决复杂问题的方法,其中简单工厂模式和工厂方法模式是两种常用的创建型模式。在这篇文章中,我们将结合这两种模式,通过一个实际案例,展示如何有效地创建和管理对象。

背景与问题描述

假设我们正在开发一个跨平台的应用程序,需要支持不同类型的组件(例如按钮和窗口),而且要根据不同的配置来决定使用哪种平台实现。我们希望通过相同的接口来使用它们,从而简化代码和提高灵活性。

问题

直接在客户端代码中使用 new 关键字来创建不同平台的组件会导致代码耦合度高,不易扩展。如果未来需要支持新的平台(例如 Linux),就必须修改客户端代码,这违反了开闭原则。

解决方案

我们可以结合使用简单工厂模式和工厂方法模式。通过简单工厂来选择具体的工厂类,然后由具体工厂类通过工厂方法创建具体的产品对象。

设计与实现

产品接口

首先,定义按钮和窗口的接口。

// 按钮接口
public interface Button {void render();void onClick();
}// 窗口接口
public interface Window {void render();
}

具体产品类

接下来,实现不同平台的具体产品类。

// Windows 按钮
public class WindowsButton implements Button {public void render() {System.out.println("Render a button in Windows style.");}public void onClick() {System.out.println("Handle button click in Windows style.");}
}// Mac 按钮
public class MacButton implements Button {public void render() {System.out.println("Render a button in macOS style.");}public void onClick() {System.out.println("Handle button click in macOS style.");}
}// Windows 窗口
public class WindowsWindow implements Window {public void render() {System.out.println("Render a window in Windows style.");}
}// Mac 窗口
public class MacWindow implements Window {public void render() {System.out.println("Render a window in macOS style.");}
}

抽象工厂类

定义创建按钮和窗口的抽象工厂类。

// 抽象工厂类
public abstract class GUIFactory {public abstract Button createButton();public abstract Window createWindow();
}

具体工厂类

实现不同平台的具体工厂类。

// Windows 工厂
public class WindowsFactory extends GUIFactory {public Button createButton() {return new WindowsButton();}public Window createWindow() {return new WindowsWindow();}
}// Mac 工厂
public class MacFactory extends GUIFactory {public Button createButton() {return new MacButton();}public Window createWindow() {return new MacWindow();}
}

简单工厂类

使用简单工厂类来选择具体的工厂。

public class GUIFactorySimpleFactory {public static GUIFactory getFactory(String osType) {if (osType.equalsIgnoreCase("Windows")) {return new WindowsFactory();} else if (osType.equalsIgnoreCase("Mac")) {return new MacFactory();} else {throw new IllegalArgumentException("Unknown OS type.");}}
}

客户端代码

在客户端代码中使用简单工厂选择具体工厂,然后通过工厂方法创建产品对象。

public class Application {private Button button;private Window window;public Application(GUIFactory factory) {button = factory.createButton();window = factory.createWindow();}public void render() {button.render();window.render();}public static void main(String[] args) {// 选择操作系统类型String osType = "Windows"; // 这个可以根据配置文件或运行时参数来决定// 使用简单工厂获取具体工厂GUIFactory factory = GUIFactorySimpleFactory.getFactory(osType);// 使用工厂方法创建具体产品Application app = new Application(factory);app.render();}
}

总结

通过将简单工厂和工厂方法结合使用,我们可以实现更灵活和可扩展的对象创建方式。在这个例子中,简单工厂用于选择具体的工厂,而具体工厂通过工厂方法来创建产品对象。这种组合方式不仅降低了客户端代码与具体类之间的耦合度,还使得系统更易于扩展和维护。

希望这个例子能帮助你更好地理解简单工厂和工厂方法的结合使用。如果你觉得这篇文章对你有帮助,请给我点个关注和赞!谢谢!

相关文章:

结合简单工厂和工厂方法模式:实现灵活的对象创建

前言 在软件开发过程中,创建对象的方式直接影响代码的灵活性和可维护性。设计模式提供了一种解决复杂问题的方法,其中简单工厂模式和工厂方法模式是两种常用的创建型模式。在这篇文章中,我们将结合这两种模式,通过一个实际案例&a…...

网抑云特殊版,登录即永久

前言 今天分享一款特殊版本的音乐软件,相信大家在听网抑云的时候会有两大烦恼, 一是歌曲需要开通VIP才可以收听,不管怎么说也是国内厂商普遍操作 但是第二种烦恼你万万想不到的是,开通了会员后,惊奇的发现&#xff…...

Kotlin 实战小记:No-Arg 引用解决 No constructor found的问题

一、问题 新的项目试用一下kotlin, 调用数据库查询数据的时候报了这个问题:org.mybatis.spring.MyBatisSystemException: nested exception is org.apache.ibatis.executor.ExecutorException: No constructor found in com.neusoft.collect.entity.cm.CmRoom matc…...

HTML(5)——列表表格

列表 无序列表 作用:布局排列整齐的不需要规定顺序的区域。 标签:ul嵌套il,ul是无序列表,li是列表条目 注:ul标签只能包裹li标签,li标签可以包含任何内容 有序列表 作用:布局排列整齐的需…...

FreeBSD通过CBSD管理低资源容器jail来安装Ubuntu子系统实践

简介 FreeBSD、CBSD、Jail和Ubuntu,四者的组合方案可以说是强强联合,极具性价比和竞争力!同时安装简单方便,整体方案非常先进。 CBSD是为FreeBSD jail子系统、bhyve、QEMU/NVMM和Xen编写的管理层。该项目定位为一个综合解决方案…...

SpringCloud总结(springcloud alibaba)

目录 版本说明(很重要) springcloud alibaba对应组件版本说明 简述 spring cloud albaba 几大模块 周会讨论 - spring cloud alibaba每周都会有周会讨论,社区活跃 spring cloud alibaba官网 注册配置中心 简单介绍 nacos 步骤 示例代码 依赖…...

轻轻松松上手的LangChain学习说明书

本文为笔者学习LangChain时对官方文档以及一系列资料进行一些总结~覆盖对Langchain的核心六大模块的理解与核心使用方法,全文篇幅较长,共计50000字,可先码住辅助用于学习Langchain。 一、Langchain是什么? 如今各类AI…...

全面对比与选择指南:Milvus、PGVector、Zilliz及其他向量数据库

本文全面探讨了Milvus、PGVector、Zilliz等向量数据库的特性、性能、应用场景及选型建议,通过详细的对比分析,帮助开发者和架构师根据具体需求选择最合适的向量数据库解决方案。 文章目录 向量数据库概述向量数据库的关键功能向量数据库的扩展和选择向量…...

svm 超参数

https://www.cnblogs.com/ChevisZhang/p/12932674.html https://wenku.baidu.com/view/b8a2c73cfd4733687e21af45b307e87100f6f861.html?wkts1718332423081&bdQuerysvm%E7%9A%84%E8%B6%85%E5%8F%82%E6%95%B0 用交叉验证找到最好的参数 C 和γ 。使用 RBF 核时&#xff0c…...

001-基于Sklearn的机器学习入门:Sklearn库基本功能和标准数据集

本节将介绍Sklearn库基本功能,以及其自带的几个标准数据集的调用方法。本节是学习后面内容的基础,如果您已经对本节内容相当熟悉,可跳过本节内容。 1.1 Sklearn库基本功能 的 1.2 Sklearn库标准数据集 Sklearn自带许多标准数据集&#xff…...

充电学习—7、BC1.2 PD协议

BC1.2(battery charging)充电端口识别机制: SDP、CDP、DCP 1、VBUS detect:vbus检测 PD(portable device,便携式设备)中有个检测VBUS是否有效的电路,电路有个参考值,高…...

技术点梳理0618

ann建库,分布式建库,性能优化,precision recall参数优化 hnsw,图索引 1. build a)确定层:类似跳表思路建立多层,对每一个插入的节点,random层号l,从图的起始点search_…...

石英砂酸洗提纯方法和工艺

石英砂酸洗提纯方法和工艺是石英砂加工中至关重要的一个环节,其目的是通过化学手段去除石英砂中的杂质,提升其纯度。以下将详细介绍石英砂酸洗提纯的方法和工艺,以便更好地理解和应用这一技术。 一、概述 石英砂酸洗提纯主要是利用酸液对石英…...

linux安装dgl

1.DGL官网、选择与自己cuda、python版本匹配的dgl的whl文件CUDA11.8、python10并下载 2.用pip install运行 pip install /home/u2023170749/download/dgl-2.2.0cu118-cp310-cp310-manylinux1_x86_64.whl或者直接安装https://blog.csdn.net/weixin_44017989/article/details/13…...

【SAP-ABAP】-权限批导-批量给某个角色导入事务码权限

需求:SAP期初上线的时候,业务顾问经常会遇到批量创建角色和分配角色权限的情况 岗位需求:一般是业务顾问定义权限,BASIS进行后期运维,今天讲两个批导功能,方便期初上线 主要函数:PRGN_READ_ROLE…...

异常处理总结

自定义异常 ​ 系统中的异常可以分为我们能预知的异常和未知的系统异常,对于我们能预知的异常如空值判断,用户名错误,密码错误等异常我们需要返回客户端,对于系统内部异常如SQL语法错误,参数格式转换错误等需要统一包…...

大模型日报2024-06-18

大模型日报 2024-06-18 大模型资讯 大模型产品 Olvy 3.0:AI加速客户反馈分析 摘要: Olvy 3.0推出AI自动监听和智能标签功能,通过Google Meet集成轻松提取洞察,贴近客户,激发同理心。 PlantIdentify-免费植物识别应用 摘要: PlantI…...

NumPy 双曲函数与集合操作详解

NumPy 双曲函数 NumPy 提供了 sinh()、cosh() 和 tanh() 等 ufunc,它们接受弧度值并生成相应的双曲正弦、双曲余弦和双曲正切值。 示例: import numpy as npx np.sinh(np.pi/2)print(x)示例 找到数组 arr 中所有值的双曲余弦值: import…...

ABSD-系统架构师(十三)

1、CDN和反向代理的基本原理都是()。 A缓存 B负载均衡 C路由转发 DNAT转发 答案:A 2、(必考)在ABSD(基于架构的软件开发)方法中,顶层被分解为()&#xff…...

PLC通过Profibus协议转Modbus协议网关接LED大屏通讯

一、背景 Modbus协议和Profibus协议是两种常用于工业控制系统的通信协议,它们在自动化领域中起着重要的作用。Modbus是一种串行通信协议,被广泛应用于各种设备之间的通信,如传感器、执行器、PLC等。而Profibus则是一种现场总线通信协议&…...

第二十三篇——香农第二定律(二):到底要不要扁平化管理?

目录 一、背景介绍二、思路&方案三、过程1.思维导图2.文章中经典的句子理解3.学习之后对于投资市场的理解4.通过这篇文章结合我知道的东西我能想到什么? 四、总结五、升华 一、背景介绍 对于企业的理解,扁平化的管理,如果从香农第二定律…...

stm32f103 HAL库 HC-SR04测距

目录 一、实现测距二、添加TIM3控制LED根据距离以不同频率闪烁三、观察时序Modebus协议12路超声波雷达设计方案1. 系统架构设计2. 硬件设计3. 软件设计4. 通信协议设计5. 用户接口6. 安全和冗余7. 测试和验证8. 电源和物理封装9. 文档和支持 一、实现测距 配置时钟 配置定时器…...

vue中通过自定义指令实现一个可拖拽,缩放的弹窗

效果 功能描述 按住头部可拖拽鼠标放到边框,可缩放多层重叠丰富的插槽,易于扩展 示例 指令代码 export const dragDialog {inserted: function (el, { value, minWidth 400, minHeight 200 }) {// 让弹窗居中let dialogHeight el.clientHeight ?…...

FreeRtos-09事件组的使用

1. 事件组的理论讲解 事件组:就是通过一个整数的bit位来代表一个事件,几个事件的or和and的结果是输出 #define configUSE_16_BIT_TICKS 0 //configUSE_16_BIT_TICKS用1表示16位,用0表示32位 1.1 事件组适用于哪些场景 某个事件若干个事件中的某个事件若干个事件中的所有事…...

多路h265监控录放开发-(1)建立head窗口并实现鼠标拖动整个窗口

头文件: //鼠标事件 用于拖动窗口//一下三个函数都是QWidget的可重载成员函数void mouseMoveEvent(QMouseEvent* ev) override;void mousePressEvent(QMouseEvent* ev) override;void mouseReleaseEvent(QMouseEvent* ev) override; 源文件: / /// 鼠标…...

ICMR 2024在普吉岛闭幕,学者与泰国舞者共舞,燃爆全场

惊艳!ICMR 2024在普吉岛闭幕,学者与泰国舞者共舞,燃爆全场! 会议之眼 快讯 ICMR(International Conference on Multimedia Retrieval)即国际多媒体检索会议,是一个专注于多媒体检索领域的顶级…...

大模型精调:实现高效迁移学习的艺术

在人工智能领域,大型预训练模型(以下简称“大模型”)已经取得了令人瞩目的成果。这些模型通过在海量数据上进行预训练,能够捕捉到丰富的特征信息,为各种下游任务提供强大的支持。然而,如何将这些大模型应用…...

epoll服务端和客户端示例代码

epoll 服务端demo #include <stdio.h> #include <sys/epoll.h> #include <sys/socket.h> #include <sys/types.h> #include <netinet/in.h> #include <arpa/inet.h> #include <fcntl.h> #include <unistd.h> #include <ne…...

最大乘积和-第13届蓝桥杯省赛Python真题精选

[导读]&#xff1a;超平老师的Scratch蓝桥杯真题解读系列在推出之后&#xff0c;受到了广大老师和家长的好评&#xff0c;非常感谢各位的认可和厚爱。作为回馈&#xff0c;超平老师计划推出《Python蓝桥杯真题解析100讲》&#xff0c;这是解读系列的第85讲。 最大乘积和&#…...

探索C嘎嘎的奇妙世界:第四关---引用与内联函数

1 引用: 引用不是新定义一个变量&#xff0c;而是给已存在变量取了一个别名&#xff0c;编译器不会为引用变量开辟内存空间&#xff0c;它和它引用的变量共用同一块内存空间。 #include<iostream> using namespace std;int main() {int a 0;// 引用&#xff1a;…...

有没有专门建设网站的公司/友链通

1、打开OU组策略编辑器(第二篇中找怎么打开组策略编辑器)&#xff0c;展开用户配置---软件设置--软件安装&#xff0c;右击软件安装---属性&#xff0c;打开软件安装 属性对话框&#xff0c;在默认程序包位置下点击浏览&#xff0c;指定软件安装包存放在服务器(服务器IP地址为1…...

制作网站首先做的是/游戏推广员怎么做

HTML 标签Internet Explorer 10, Firefox, Opera, Chrome 以及 Safari 6 支持 标签。注释&#xff1a;Internet Explorer 9 以及更早的版本不支持 标签。 ( 推荐学习&#xff1a;html教程 )定义和用法标签标示任务的进度(进程)。HTML 4.01 与 HTML 5 之间的差异标签是 HTML 5 中…...

东莞外贸企业做网站/微信营销怎么做

1、下载安装Geoserver 主页地址&#xff1a;http://geoserver.org/ 下载地址 https://jaist.dl.sourceforge.net/project/geoserver/GeoServer/2.15.1/geoserver-2.15.1.exe 2、直接安装 选择jdk的安装位置 C:\Program Files\Java\jdk1.8.0_181 2、最后&#xff0c;在浏览器…...

ppt可以做网站吗/企业培训课程设置

本章介绍数据库中的各种制约。若要强制数据库的完整性&#xff0c;一组规则的定义&#xff0c;也就是所谓约束。约束即允许或禁止在所述列中的值。在实时数据库活动&#xff0c;该数据应该有一定的限制被添加。例如&#xff0c;在一个销售数据库&#xff0c;销售-ID或事务id应该…...

网络绿化网站建设哪家权威/百度推广助手app

思路&#xff1a;1、获取元素。2、用for循环历遍数组&#xff0c;把checkbox的checked设置为true即实现全选&#xff0c;把checkbox的checked设置为false即实现不选。3、通过if判断&#xff0c;如果checked为true选中状态的&#xff0c;就把checked设为false不选状态&#xff0…...

个人免费发布房源信息/福州百度关键词优化

默认访问的就是resources的路径下面的内容 参考文章&#xff1a;https://blog.csdn.net/liulang68/article/details/109240568...