设计模式 - 工厂模式 精准梳理精准记忆

news2025/3/13 5:22:04

在这里插入图片描述

在这里插入图片描述

                                                         1、代码片段 - 带入理解


一、核心模式分类

  1. 简单工厂模式(编程习惯,非 GoF 设计模式)
  2. 工厂方法模式(GoF 创建型模式)
  3. 抽象工厂模式(GoF 创建型模式)


二、演变过程:咖啡店案例

初始实现

// 咖啡基类
abstract class Coffee {
     public abstract String getName();
}

class AmericanCoffee extends Coffee {}
class LatteCoffee extends Coffee {}

// 咖啡店直接创建对象
class CoffeeStore {
     public Coffee orderCoffee(String type) {
          if ("american".equals(type)) {
               return new AmericanCoffee();
          } else {
               return new LatteCoffee();
          }
     }
}

问题   违反开闭原则,新增咖啡类型需修改订单方法



三、改进方案演变

1、简单工厂模式

class SimpleCoffeeFactory {
    public Coffee createCoffee(String type) {
        // 创建逻辑...
    }
}

class CoffeeStore {
    private SimpleCoffeeFactory factory;
    public Coffee orderCoffee(String type) {
        return factory.createCoffee(type);
    }
}
  • 优点   解耦对象创建
  • 缺点  仍需修改工厂代码,违反开闭原则

2、工厂方法模式

interface CoffeeFactory {
    Coffee createCoffee();
}

class AmericanFactory implements CoffeeFactory {
    public Coffee createCoffee() { return new AmericanCoffee(); }
}

class CoffeeStore {
    private CoffeeFactory factory;
    public void setFactory(CoffeeFactory factory) {
        this.factory = factory;
    }
    public Coffee orderCoffee() {
        return factory.createCoffee();
    }
}
  • 优点   完全遵循开闭原则
  • 缺点   类数量激增(类爆炸问题)

3、抽象工厂模式

interface DessertFactory {
    Coffee createCoffee();
    Dessert createDessert();
}

class AmericanDessertFactory implements DessertFactory {
    public Coffee createCoffee() { return new AmericanCoffee(); }
    public Dessert createDessert() { return new MatchaMousse(); }
}
  • 优点   管理产品族(咖啡+甜点的组合)
  • 代价   新增产品类型需修改所有工厂接口

4、模式对比表

模式特性简单工厂工厂方法抽象工厂
扩展性修改工厂类新增工厂子类新增工厂实现类
产品维度单一产品单一产品产品族(多相关产品)
开闭原则违反遵循部分遵循
复杂度
典型应用场景简单对象创建需要灵活扩展的产品创建系列关联产品的组合创建


四、进阶应用技巧

1、静态工厂

class SimpleCoffeeFactory {
     public static Coffee createCoffee(String type) {
          // 创建逻辑...
     }
}

2、配置化工厂

# bean.properties
american=com.example.AmericanCoffee
latte=com.example.LatteCoffee
class ConfigFactory {
     private static Map<String, Coffee> cache = new HashMap<>();

     static {
          // 加载配置文件,反射创建对象存入缓存
     }

     public static Coffee getCoffee(String key) {
          return cache.get(key);
     }
}

全部代码

public class CoffeeFactory {
     // 加载配置文件, 获取配置文件中配置的全类名, 并创建该类的对象进行存储
     // 1.定义容器对象用来存储咖啡对象
     private static HashMap<String, Coffee> map = new HashMap<String, Coffee>();

     // 2.加载配置文件, 只需要加载一次
     static {
          // 2.1 创建proper.ties 对象
          Properties p = new Properties();
          // 2.2调用p对象中的load 方法进行配置文件的加载   获取字节码 -> 获取类加载器 -> 获取目标资源(返回inputStream)
          InputStream is = CoffeeFactory.class.getClassLoader().getResourceAsStream("bean.properties");
          try {
               // 加载资源
               p.load(is);
               // 从p集合中获取全类名并创建对象
               Set<Object> keys = p.keySet();
               for (Object key : keys) {
                    String className = p.getProperty((String) key);
                    // 通过反射创建对象
                    Class<?> clazz = Class.forName(className);
                    Coffee coffee = (Coffee) clazz.newInstance();// 创建对象
                    // 将名称和对象存储到容器中
                    map.put((String) key,coffee);
               }
          } catch (IOException | ClassNotFoundException | InstantiationException | IllegalAccessException e) {
               e.printStackTrace();
          }
     }

     // 根据名称获取对象
     public static Coffee createCoffee(String name){
          return map.get(name);
     }
}


五、JDK典型案例

  1. 集合迭代器
// 工厂方法模式应用
Collection<String> coll = new ArrayList<>();
Iterator<String> it = coll.iterator(); // ArrayList内部实现Iterator
  1. 日期工具
Calendar cal = Calendar.getInstance(); // 根据时区返回不同实现
DateFormat df = DateFormat.getInstance();




                                                         2、文字提炼 - 记忆切入点


一、简单工厂模式

1、核心思想

将对象创建逻辑集中在一个"工厂类"中,通过 参数 控制具体产品类型。

  • 关键步骤

    1. 定义产品接口
      创建抽象基类(如 Coffee),声明所有产品共有的方法(如 getName()

    2. 实现具体产品
      继承基类创建具体产品(如 AmericanCoffeeLatteCoffee),各自实现特有逻辑

    3. 构建工厂类
      创建 SimpleCoffeeFactory 类,内部包含静态/实例方法(如 createCoffee(type)),通过 if-elseswitch 判断参数类型,返回对应的具体产品实例

    4. 客户端调用
      客户端(如CoffeeStore)持有工厂引用,调用createCoffee()时传入类型参数,无需直接接触具体产品类

  • 典型特征

    • 工厂类包含所有产品的创建逻辑

    • 新增产品必须修改工厂类代码



二、工厂方法模式

2、核心思想

将对象的创建 延迟 到子类,每个产品对应一个专属工厂。

  • 关键步骤

    1. 定义抽象工厂接口
      创建CoffeeFactory接口,声明抽象方法(如createCoffee()

    2. 实现具体工厂
      为每个产品创建专属工厂类(如AmericanCoffeeFactoryLatteCoffeeFactory),在createCoffee()中返回对应的具体产品实例

    3. 客户端依赖抽象
      客户端类(如CoffeeStore)持有工厂接口的引用,通过setFactory()方法注入具体工厂

    4. 动态创建产品
      客户端调用factory.createCoffee()时,实际执行的是具体工厂类中实现的创建逻辑

  • 典型特征

    • 每个产品对应一个独立工厂类

    • 新增产品只需添加新工厂,无需修改已有代码



三、抽象工厂模式

2、核心思想

创建相关产品族的工厂,保证产品之间的兼容性。

  • 关键步骤

    1. 定义产品族接口
      创建多个抽象产品接口(如 Coffee: 咖啡Dessert: 甜点),每个接口代表一类产品

    2. 定义抽象工厂接口
      创建DessertFactory: 甜点工厂接口,声明创建系列产品的方法(如 createCoffee()createDessert()

    3. 实现具体工厂
      为每个产品族创建工厂类(如AmericanDessertFactory: 美式甜点工厂),同时实现该族内 所有产品的创建逻辑

    4. 客户端组合使用
      客户端通过选择具体工厂,获得配套的产品组合(如美式咖啡 + 抹茶慕斯),确保产品间的兼容性

  • 典型特征

    • 一个工厂创建多个关联产品

    • 新增产品类型时, 需要修改所有工厂接口



四、工厂模式历史演进

  1. 简单工厂   解决直接 new 对象带来的耦合问题,但工厂本身成为新的耦合点
  2. 工厂方法   通过多态工厂解耦,支持扩展但容易产生类爆炸
  3. 抽象工厂   应对产品组合需求,用更高维度的抽象管理关联对象


五、记忆点 - 关键区别

  • 考虑创建目标时

    • 简单工厂   单一产品
    • 工厂方法   单一产品
    • 抽象工厂   产品族

  • 考虑扩展代价时

    • 简单工厂   修改工厂类
    • 工厂方法   新增工厂类
    • 抽象工厂   修改所有工厂接口

  • 考虑设计重心时

    • 简单工厂   创建逻辑集中化
    • 工厂方法   创建责任分散化
    • 抽象工厂  产品组合约束



提炼

模式选择指南

  1. 简单工厂   适用于对象创建逻辑简单,不需要频繁扩展
  2. 工厂方法   适合需要灵活扩展产品类型的场景
  3. 抽象工厂   适用于管理产品族,强调相关产品必须配套使用

关键设计原则体现

  1. 开闭原则   工厂方法模式的典型体现
  2. 单一职责   每个工厂只负责创建特定对象
  3. 依赖倒置   客户端依赖抽象接口而非具体实现

如果这篇文章帮到你, 帮忙点个关注呗, 不想那那那点赞或收藏也行鸭 (。•̀ᴗ-)✧ ~

在这里插入图片描述

在这里插入图片描述 在这里插入图片描述 在这里插入图片描述 在这里插入图片描述
                                                                                                                                   '(இ﹏இ`。)

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

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

相关文章

NVIDIA(英伟达) GPU 芯片架构发展史

GPU 性能的关键参数 CUDA 核心数量&#xff08;个&#xff09;&#xff1a;决定了 GPU 并行处理能力&#xff0c;在 AI 等并行计算类业务下&#xff0c;CUDA 核心越多性能越好。 显存容量&#xff08;GB&#xff09;&#xff1a;决定了 GPU 加载数据量的大小&#xff0c;在 AI…

springboot项目使用中创InforSuiteAS替换tomcat

springboot项目使用中创InforSuiteAS替换tomcat 学习地址一、部署InforSuiteAS1、部署2、运行 二、springboot项目打包成war包 特殊处理1、pom文件处理1、排除内嵌的tomcat包2、新增tomcat、javax.servlet-api3、打包格式设置为war4、打包后的项目名称5、启动类修改1、原来的不…

Tomcat-web服务器介绍以及安装部署

一、Tomcat简介 Tomcat是Apache软件基金会&#xff08;Apache Software Foundation&#xff09;的Jakarta 项目中的一个核心项目&#xff0c;由Apache、Sun和其他一些公司及个人共同开发而成。 Tomcat服务器是一个免费的开放源代码的Web应用服务器&#xff0c;属于轻量级应用…

18类创新平台培育入库!长沙经开区2025年各类科技创新平台培育申报流程时间材料及申报条件

长沙经开区打算申报企业研发中心、技术创新中心、工程技术研究中心、新型研发机构、重点实验室、概念验证中心和中试平台、工程研究中心、企业技术中心、制造业创新中心、工业设计中心等创新平台的可先备案培育入库&#xff0c;2025年各类平台的认定将从培育库中优先推荐&#…

使用 Elasticsearch 进行集成测试初始化​​数据时的注意事项

作者&#xff1a;来自 Elastic piotrprz 在创建应该使用 Elasticsearch 进行搜索、数据聚合或 BM25/vector/search 的软件时&#xff0c;创建至少少量的集成测试至关重要。虽然 “模拟索引” 看起来很诱人&#xff0c;因为测试甚至可以在几分之一秒内运行&#xff0c;但它们实际…

9. Flink的性能优化

1. Flink的资源和代码优化 1.1 slot资源配置 Flink中具体跑任务的进程叫TaskManager&#xff0c;TM进程又会根据配置划分出诺干个TaskSlot&#xff0c;它是具体运行SubTask的地方。slot是Flink用来隔离各个subtask的资源集合&#xff0c;这里的资源一把指内存&#xff0c;TCP…

【文生图】windows 部署stable-diffusion-webui

windows 部署stable-diffusion-webui AUTOMATIC1111 stable-diffusion-webui Detailed feature showcase with images: 带图片的详细功能展示: Original txt2img and img2img modes 原始的 txt2img 和 img2img 模式 One click install and run script (but you still must i…

华为:Wireshark的OSPF抓包分析过程

一、OSPF 的5包7状态 5个数据包 1.Hello&#xff1a;发现、建立邻居&#xff08;邻接&#xff09;关系、维持、周期保活&#xff1b;存在全网唯一的RID&#xff0c;使用IP地址表示 2.DBD&#xff1a;本地的数据库的目录&#xff08;摘要&#xff09;&#xff0c;LSDB的目录&…

视频输入设备-V4L2的开发流程简述

一、摄像头的工作原理与应用 基本概念 V4L2的全称是Video For Linux Two&#xff0c;其实指的是V4L的升级版&#xff0c;是linux系统关于视频设备的内核驱动&#xff0c;同时V4L2也包含Linux系统下关于视频以及音频采集的接口&#xff0c;只需要配合对应的视频采集设备就可以实…

浅论数据库聚合:合理使用LambdaQueryWrapper和XML

提示&#xff1a;文章写完后&#xff0c;目录可以自动生成&#xff0c;如何生成可参考右边的帮助文档 文章目录 前言一、数据库聚合替代内存计算&#xff08;关键优化&#xff09;二、批量处理优化四、区域特殊处理解耦五、防御性编程增强 前言 技术认知点&#xff1a;使用 XM…

CentOS 7.9 安装 ClickHouse 文档

1. 环境准备 确保系统为 CentOS 7.9&#xff0c;并已安装 Docker。如果未安装 Docker&#xff0c;请先安装 Docker。 安装 Docker # 卸载旧版本 Docker&#xff08;如果有&#xff09; sudo yum remove -y docker docker-client docker-client-latest docker-common docker-…

WPS条件格式:B列的值大于800,并且E列的值大于B列乘以0.4时,这一行的背景标红

一、选择数据区域 选中需要应用条件格式的区域&#xff08;例如A2:E100 &#xff09;。 二、打开条件格式 点击“开始”选项卡&#xff0c;选择“条件格式” > “新建规则”。 三、选择规则类型 选择“使用公式确定要设置格式的单元格”。 四、输入公式 在公式框中输入以…

MWC 2025 | 紫光展锐联合移远通信推出全面支持R16特性的5G模组RG620UA-EU

2025年世界移动通信大会&#xff08;MWC 2025&#xff09;期间&#xff0c;紫光展锐联合移远通信&#xff0c;正式发布了全面支持5G R16特性的模组RG620UA-EU&#xff0c;以强大的灵活性和便捷性赋能产业。 展锐芯加持&#xff0c;关键性能优异 RG620UA-EU模组基于紫光展锐V62…

AI-Ollama本地大语言模型运行框架与Ollama javascript接入

1.Ollama Ollama 是一个开源的大型语言模型&#xff08;LLM&#xff09;平台&#xff0c;旨在让用户能够轻松地在本地运行、管理和与大型语言模型进行交互。 Ollama 提供了一个简单的方式来加载和使用各种预训练的语言模型&#xff0c;支持文本生成、翻译、代码编写、问答等多种…

PROFINET转PROFIBUS从案例剖析网关模块的协议转换功能

一、 案例背景 在当下追求高效协同的工业自动化生产体系里&#xff0c;设备间的无缝互联互通堪称关键要素。某企业的生产车间中&#xff0c;有一台性能稳定的变频器&#xff0c;其配备的是PROFIBUS接口。与此同时&#xff0c;操控整个生产线的核心大脑——西门子1500 PLC&…

VEC系列-RabbitMQ 入门笔记

消息队列&#xff08;MQ&#xff09;对于开发者来说是一个经常听到的词汇&#xff0c;但在实际开发中&#xff0c;大多数人并不会真正用到它。网上已经有很多关于 MQ 概述和原理的详细讲解&#xff0c;官网文档和技术博客也都介绍得很深入&#xff0c;因此&#xff0c;我在这里…

第5章 使用OSSEC进行监控(网络安全防御实战--蓝军武器库)

网络安全防御实战--蓝军武器库是2020年出版的&#xff0c;已经过去3年时间了&#xff0c;最近利用闲暇时间&#xff0c;抓紧吸收&#xff0c;总的来说&#xff0c;第5章开始进入主机安全&#xff08;HIDS&#xff09;领域了&#xff0c;2022年的时候有幸做过终端安全一段时间&a…

安装IK分词器;IK分词器配置扩展词库:配置扩展字典-扩展词,配置扩展停止词字典-停用词

安装IK分词器&#xff1b;IK分词器配置扩展词库&#xff1a;配置扩展字典-扩展词&#xff0c;配置扩展停止词字典-停用词 安装IK分词器IK分词配置扩展词库配置扩展字典-扩展词配置停止词字典-停用词测试配置字典前配置字典后 本文 ElasticSearch 版本为&#xff1a;7.17.9&…

pgsql行列转换

目录 一、造测试数据 二、行转列 1.函数定义 2.语法 3.示例 三、列转行 1.函数定义 2.语法 3.示例 一、造测试数据 create table test ( id int, json1 varchar, json2 varchar );insert into test values(1,111,{111}); insert into test values(2,111,222,{111,22…

Nginx 开启Baise认证

开启Baise认证 需要再站点Server配置中添加一下配置&#xff0c;添加htpasswd文件 server{auth_basic "HTTP Basic Authentication";auth_basic_user_file /etc/nginx/htpasswd;# 其他配置信息... }如果你的 Linux 服务器没有安装 htpasswd 工具&#xff0c;可以通…