设计模式-创建型模式之工厂设计模式

文章目录

    • 五、工厂方法
    • 六、抽象工厂

五、工厂方法

工厂方法,使用工厂可以像使用人员屏蔽对象创建的细节,使用者无需指定具体的类即可使用功能,达到信息隐蔽的作用,便于后期的维护,修改和扩展

在看工厂方法前还有一类是 简单工厂,相当于是一个工厂中有各种产品,创建在一个类中,客户无需知道具体产品的名称,只需要知道产品类所对应的参数即可。但是工厂的职责过重,而且当类型过多时不利于系统的扩展维护。
在这里插入图片描述

比如我们在聚合支付的时候有,微信支付和支付宝支付,在不同的选择要获取不同的对象,如果用简单方法来实现的话:

  1. 先定义统一的支付抽象类,定义支付和取消支付抽象方法
public interface PayInterFace {//支付void pay();//取消支付void cancelPay();
}
  1. 定义微信支付类
public class WxPay implements PayInterFace {@Overridepublic void pay() {System.out.println("微信支付中...");}@Overridepublic void cancelPay() {System.out.println("微信取消支付!");}
}
  1. 定义支付宝类
public class ZfbPay implements PayInterFace {@Overridepublic void pay() {System.out.println("支付宝支付中...");}@Overridepublic void cancelPay() {System.out.println("支付宝取消支付!");}
}
  1. 创建简单工厂
public class SimplePayFactory {public static PayInterFace getPay(String payType) {if (Objects.equals(payType, "wx")) {return new WxPay();} else if (Objects.equals(payType, "zfb")) {return new ZfbPay();} else {return null;}}
}
  1. 使用
public class demo {public static void main(String[] args) {PayInterFace pay = SimplePayFactory.getPay("wx");pay.pay();pay.cancelPay();PayInterFace pay1 = SimplePayFactory.getPay("zfb");pay1.pay();pay1.cancelPay();}
}

在这里插入图片描述

通过传入不同的标识获取不同的对象,且无需指定具体对象,让使用者无需关注创建对象的细节,增加对象需要在工厂中添加对应的实例化程序,当类型过多时不利于系统的扩展维护。

那下面来看下工厂方法的做法:

  1. 在上面的基础上,再建立 支付工厂接口:
public interface PayFactory {PayInterFace getPay();
}
  1. 建立微信支付工厂
public class WxPayFactory implements PayFactory {@Overridepublic PayInterFace getPay() {return new WxPay();}
}
  1. 建立支付宝工厂
public class ZfbPayFactory implements PayFactory {@Overridepublic PayInterFace getPay() {return new ZfbPay();}
}
  1. 使用
public class demo {public static void main(String[] args) {PayInterFace pay = new WxPayFactory().getPay();pay.pay();pay.cancelPay();PayInterFace pay1 = new ZfbPayFactory().getPay();pay1.pay();pay1.cancelPay();}
}

这种方式同样屏蔽了对象建立的细节,且无需指定具体对象,但相对于上面的简单工厂,更易于做扩展,比如要引入新的支付,只需要创建新的工厂并实现PayFactory 即可,更利于系统的扩展。

六、抽象工厂

上面学习了简单工厂工厂方法,下面来看下抽象工厂
抽象工厂模式(Abstract Factory Pattern)是围绕一个超级工厂创建其他工厂。该超级工厂又称为其他工厂的工厂。

在抽象工厂模式中,接口是负责创建一个相关对象的工厂,不需要显式指定它们的类。每个生成的工厂都能按照工厂模式提供对象。

在上面的场景中,加入支付后需要扣除库存,就需要引入库存工厂,并调用扣除库存的方法,库存工厂和支付工厂貌似不相干,但在抽象工厂中,抽象工厂相当于一个公司,库存和支付相当与部门,相对于公司来看,支付和库存都是公司下的部门,是一个整体。所以抽象工厂就是定义一个产品组,可以完成一系列的过程,而不是单一的活动。

下面使用抽象工厂定义支付后扣除库存的设计:

  1. 定义库存操作接口
public interface RepertoryInterFace {void deductRepertory();
}
  1. 以苹果为例,定义具体库存为苹果的库存
public class AppleRepertory implements RepertoryInterFace {@Overridepublic void deductRepertory() {System.out.println("苹果库存 扣除库存...");}
}
  1. 定义抽象工厂,定义支付和扣库存抽象方法
public interface BuyAbstractFactory {//支付PayInterFace pay();//扣库存RepertoryInterFace deductRepertory();
}
  1. 定义抽象工厂实现,这里演示效果,直接采用微信支付对象
public class BuyAbstractFactoryImpl implements BuyAbstractFactory {@Overridepublic PayInterFace pay() {return new WxPay();}@Overridepublic RepertoryInterFace deductRepertory() {return new AppleRepertory();}
}
  1. 使用
public class demo {public static void main(String[] args) {BuyAbstractFactory factory = new BuyAbstractFactoryImpl();factory.pay().pay();factory.deductRepertory().deductRepertory();}
}

在这里插入图片描述

使用抽象工厂方式,颗粒化程度大,让使用者无需知道整个工作组的对象,即可完成一连串的操作,对可扩展性,可修改修都很友好

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

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

相关文章

华纳云:linux中怎么实现apache安装与配置

在 Linux 系统中,安装和配置 Apache HTTP 服务器通常涉及以下步骤。以下以 Ubuntu 为例,其他 Linux 发行版的步骤也大致相同。 步骤 1:安装 Apache 打开终端并运行以下命令: sudo apt update sudo apt install apache2 步骤 …

Java实现堆

堆是一种基于完全二叉树的数据结构,它分为大根堆和小根堆。在大根堆中,每个节点的值都大于或等于其子节点的值;而在小根堆中,每个节点的值都小于或等于其子节点的值。 在Java中,我们可以使用数组来表示堆。由于完全二…

网工内推 | 云计算运维,云相关认证优先,最高30K,带薪年假

01 安畅网络 招聘岗位:云计算运维工程师 职责描述: 1、负责对公有云平台的计算、存储、网络资源等IAAS/SAAS/PAAS层产品组件日常交付部署运维工作,包括调试、配置、维护、监控、优化等工作; 2、负责对操作系统及应用日常运行维护…

MySQL事务详解

MySQL事务详解 数据库事务概述事务是如何实现的事务的ACID特性事务的状态 事务的使用显式事务隐式事务示例自动提交回滚回滚到保存点 事务的隔离级别数据并发问题MySQL 支持的四种隔离级别注意示例 设置隔离级别 事务的常见分类 数据库事务概述 数据库事务是数据库管理系统&am…

《山水间的家》第二季收官,国台酒业解锁中国式浪漫

执笔 | 洪大大 编辑 | 萧 萧 近日,由国台酒特别支持的大型文旅探访节目《山水间的家》第二季在总台央视综合频道(CCTV-1)正式收官。 第二季节目以家庭为视角切入,先后走进江苏、四川、重庆、江西、湖北、贵州、浙江等地24个特色…

Python subprocess模块的高级玩法

Python的subprocess模块是一个非常强大的工具,用于启动和与外部进程进行交互。它允许执行外部命令、访问系统Shell、管道数据、捕获输出和错误信息,以及更多。 本文详细介绍 subprocess模块的各个方面,包括如何执行外部命令、传递参数、处理…

Redis安装和部署详细流程

文章目录 一、Windows环境下安装 Redis1.1 下载Redis1.2 启动redis服务器1.3 启动redis客户端1.4 配置环境变量 参考资料 一、Windows环境下安装 Redis windows系统环境下,redis安装方式主要有: zip压缩包方式 https://redis.io/download 或者 https:/…

MMdetection3.0 问题

MMdetection3.0 问题 希望各位路过的大佬指教一下: 问题: 1、NWPU-VHR-10有标注的数据一共650张,我将其分为了455张训练集,195张验证集。 2、然后使用MMdetection3.0框架中的Faster-rcnn网络进行训练,设置训练参数b…

CityEngine2023 根据shp数据构建三维模型并导入UE5

目录 0 引言1 基本操作2 实践2.1 导入数据(.shp)2.2 构建三维模型2.3 将模型导入UE5 🙋‍♂️ 作者:海码007📜 专栏:CityEngine专栏💥 标题:CityEngine2023 根据shp数据构建三维模型…

Android问题笔记四十九:ViewPager 嵌套 Fragment 扩大滑动响应区域,避免左右滑动过于灵敏问题

Unity3D特效百例案例项目实战源码Android-Unity实战问题汇总游戏脚本-辅助自动化Android控件全解手册再战Android系列Scratch编程案例软考全系列Unity3D学习专栏蓝桥系列ChatGPT和AIGC 👉关于作者 专注于Android/Unity和各种游戏开发技巧,以及各种资源分…

finebi 新手入门案例

finebi 新手入门案例 连锁超市销售数据分析 步骤: 准备公共数据新建分析主题处理数据在数据中分析在图形中分析数据大屏 准备公共数据 点击公共数据 点击新建文件夹 修改文件夹名称 上传数据 鼠标悬停在文件夹上,右侧出现 鼠标悬停在文件夹上&#x…

git-5

1.GitHub为什么会火? 2.GitHub都有哪些核心功能? 3.怎么快速淘到感兴趣的开源项目 github上面开源项目非常多,为了我们高效率的找到我们想要的资源 根据时间 不进行登录,是没有办法享受到高级搜索中的代码功能的,登录…

maven 基础

maven常用命令 clean &#xff1a;清理 compile&#xff1a;编译 test&#xff1a;测试 package&#xff1a;打包 install&#xff1a;安装 maven坐标书写规范 <dependency> <groupId>mysql</groupId> <artifactId>mysql-connector-java</ar…

改变生活,引领未来

随着科技的飞速发展&#xff0c;人工智能&#xff08;AI&#xff09;已经深入到我们生活的各个角落&#xff0c;成为我们日常生活中不可或缺的一部分。它像一位魔术师&#xff0c;用其独特的“魔法”帮助我们解决问题、提供建议&#xff0c;甚至预测未来。本文将探讨人工智能如…

(Error Creating bean with name ‘xxx‘)类问题解决思路

学习springboot报错&#xff1a; Error creating bean with name com.atguigu.mybatislearning.MyBatisPlusServiceTest: Unsatisfied dependency expressed through field userService; 解决方式&#xff1a; 1、注解问题&#xff1a; Controller、service层的注解缺失会造…

链表中倒数第k个节点,剑指offer,力扣

目录 题目地址&#xff1a; 剑指offer原题&#xff1a; 我们直接看题解吧&#xff1a; 解题方法&#xff1a; 难度分析&#xff1a; 审题目事例提示&#xff1a; 解题思路&#xff08;双指针&#xff08;快慢指针&#xff09;&#xff09;&#xff1a; 代码实现&#xff1a; 代…

从功能测试到自动化测试,我总结了一些工作经验分享给大家

&#x1f4e2;专注于分享软件测试干货内容&#xff0c;欢迎点赞 &#x1f44d; 收藏 ⭐留言 &#x1f4dd; 如有错误敬请指正&#xff01;&#x1f4e2;交流讨论&#xff1a;欢迎加入我们一起学习&#xff01;&#x1f4e2;资源分享&#xff1a;耗时200小时精选的「软件测试」资…

【驱动】SPI驱动分析(三)-SPI关键数据类型

SPI数据类型 SPI控制器驱动结构体 struct spi_master抽象了控制器硬件&#xff0c;在SoC中的指的就是内部SPI控制器&#xff0c;当向SPI核心层注册一个SPI控制器时就需要提供这样的一个结构体变量。它的定义在 include/linux/spi/spi.h 文件&#xff0c;如下&#xff1a; /*…

python高级练习题库实验1(A)部分

文章目录 题目1代码实验结果题目2代码实验结果题目3代码实验结果题目4代码实验结果题目总结题目1 输入一个整数,用于控制输出*的个数,输入日期,按照特定格式输出 研究下面的例子,并编写一个与这些例子完全相同的程序。 代码 import datetime# ask user for length of b…

(C++20) consteval立即函数

文章目录 由来consteval立即函数上下文的常量性质lambda表达式 编译期间确定无法获取函数指针查看汇编 END 由来 在C11中推出了constexpr使得对象或者函数能够具有常量性质并能在编译器确定。但是对于constexpr修饰的函数来说&#xff0c;无法保证严格的在编译器确定。 下面这…