图解设计模式: 有趣的工厂模式

news2024/11/24 22:31:22

工厂模式 Factory Method

在工厂模式中 父子类的关系就像是生产工厂中模具一样, 由父类负责指定实例生成的方式 子类来决定生成具体的类. 具体的处理全部交给子类负责,目的就是为了将生产实例的框架和负责实例生产类解耦

示例程序

从下面这段示例来看看工厂模式到底能为我们做些什么。

类列表

image-20221219192835521

framwork包

产品类

在framework包里 定义了产品,也就是说实现了这个类的对象都可以成为产品 他们都可以被使用

public abstract class Product {
    public abstract void use();
}

工厂类

在framework中同样定义了工厂, 工厂类用来创造产品和注册产品

public abstract class Factory {
    public final Product create(String owner) {
        Product product = createProduct(owner);
        registerProduct(product);
        return product;
    }

    protected abstract Product createProduct(String owner);

    protected abstract void registerProduct(Product product);
}

IDCard包

id卡

id卡继承产品类 来体现我们框架分离的目的

public class IDcard extends Product {

    private String owner;

    IDcard(String owner) {
        System.out.println("制作" + owner + "的ID卡");
        this.owner = owner;
    }

    @Override
    public void use() {
        System.out.println("使用" + owner + "ID卡.");
    }

    public String getOwner() {
        return this.owner;
    }
}

IDCardFactory

继承工厂类 用来生产产品和注册产品。

public class IDCardFactory extends Factory {
    private List owners = new ArrayList();

    @Override
    protected Product createProduct(String owner) {
        return new IDcard(owner);
    }

    @Override
    protected void registerProduct(Product product) {
        owners.add(((IDcard) product).getOwner());
    }

    public List getOwners() {
        return owners;
    }
}

测试

public class Test {
    public static void main(String[] args) {
        IDCardFactory factory = new IDCardFactory();
        Product card1 = factory.create("小红");
        Product card2 = factory.create("小明");
        Product card3 = factory.create("小刚");
        card1.use();
        card2.use();
        card3.use();

    }
}

image-20221219195521751

工厂模式的角色

在工厂模式中 我们将编写的包分离开来了,一个为framework(框架) 一个为具体的实现

这两个包的内容是平行的 如下图

类图

image-20221219195837240

Product角色

这个角色属于框架的类型 ,它定义了工厂方法中生成的实例所持有的api 具体的处理由继承了product的角色来决定

Creator创建者

Creator 也是属于框架的类型 他负责生成产品对象的抽象类,具体如何去生成由继承创建者的子类去决定

ConcreteProduct具体的产品

属于加工的类型 他决定了生成什么样的。

ConcreteCreator(具体的创建者)

ConcteteCreator 角色属于具体加工的乙方,他负责生辰具体的产品。

拓展思路

框架与加工

支持 我们分别学习了框架与具体加工这两方面的内容 他们被分别的封装到两个包中。

我们可以用相同的框架闯江湖其他的产品和工厂, 如我们要创建电视机 和 创建电视机的工厂类,这个时候我们就需要在框架保重编写电视机包

这里我们不需要修改框架包中的代码 只需要去修改对应的实现类就行了

生成实例 方法的三种实现方式

在工厂包中的生成产品方法是抽象方法 也就是需要在子类中实现这个方法, 创建产品的实现方式一般有三种

  • 指定一个抽象方法
  • 实现默认的处理 如果自类没有实现方法 将会默认处理
  • 在处理的其中抛出异常

使用模式与开发的小Tips

在日常开发中 使用模板方法或者是工厂模式的时候,因为要多读多个类的代码,缕清逻辑变得格外的重要,通常在设计模式设计子类的时候 需要想维护这些类的人员传达明确意图,擅自修改可能会出现事故

拓展实例

给产品增加id(以100开始) 并且希望 id和产品名存储在一个对应结构

我们只需要改动具体的实现就可以了

public class IDcard extends Product {

    private String owner;
    private int idNum = 100;

    IDcard(String owner, int idNum) {
        System.out.println("制作" + owner + "(" + idNum + ")" + "的ID卡");
        this.owner = owner;
        this.idNum = idNum;
    }

    @Override
    public void use() {
        System.out.println("使用" + owner + "(" + idNum + ")" + "的ID卡");
    }


    public String getOwner() {
        return this.owner;
    }

    public int getIdNum() {
        return idNum;
    }
}

public class IDCardFactory extends Factory {
    //private List owners = new ArrayList();

    Map<Integer, String> idcard = new HashMap();
    private int idNum = 100;

    @Override
    protected synchronized Product createProduct(String owner) {
        return new IDcard(owner, idNum++);
    }

    @Override
    protected void registerProduct(Product product) {
        idcard.put(((IDcard) product).getIdNum(), ((IDcard) product).getOwner());
    }

    public Map<Integer, String> getIdcard() {
        return idcard;
    }

    //public List getOwners() {
    //    return owners;
    //}
}

image-20221219202704384

我们可以发现 我们没有改动使用的方式也没有改动框架,只是修改了实现就可以完成效果的变化,可见设计模式的思路精妙

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

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

相关文章

Codeforces Round #839 (Div. 3)

A. AB? 题意&#xff1a; t组测试每组给出以ab的形式给出算式&#xff0c;求ab的值。&#xff08;a,b都是0~9&#xff09; 代码&#xff1a; tint(input()) for i in range(t):sinput()print(eval(s)) B. Matrix Rotation 题意&#xff1a; t组测试每组给一个2*2的矩阵&…

NoSQL数据库原理与应用综合项目——Redis篇

NoSQL数据库原理与应用综合项目——Redis篇 文章目录NoSQL数据库原理与应用综合项目——Redis篇0、 写在前面1、本地数据或HDFS数据导入到Redis2、Redis数据库表操作2.1 Java API 连接Redis2.2 查询数据2.3 插入数据2.4 修改数据2.5 删除数据3、Windows远程连接Redis(Linux)4、…

谁说女生不可以学编程?维密超模放弃年薪千万,一心只当程序媛

说到IT行业&#xff0c;大家第一反应应该是程序员 谁说女生不可以学编程&#xff1f;维密超模放弃年薪千万&#xff0c;一心只当程序媛 感觉一说起IT工作者 大家都会想到一个男性的形象 但是其实 有一批脸美、胸大、腰细、腿长、还都热爱编程的妹纸正在加入你们的行列&#…

(附源码)Springboot宠物领养系统 毕业设计 241104

Springboot宠物领养系统 摘 要 如今&#xff0c;随着人们生活水平不断提高&#xff0c;人们的生活在物质满足的基础上&#xff0c;更多的人将生活的重点放在追求精神享受的过程中。于此同时&#xff0c;Internet铺天盖地的普及&#xff0c;使得这样的人纷纷通过Internet的方式去…

springboot 3.0 工程建立

springboot 3.0 工程建立 脚手架搭建 进入spring官网提供的https://start.spring.io/进行脚手架搭建。 选择 Maven进行包管理&#xff0c;语言选择JAVA&#xff0c;Spring Boot 版本选择3.0.0&#xff0c;JDK 版本选择17。并在右侧选择自己希望的依赖。结果如下图&#xff1…

基于SpringMVC+Hibernate+Layui城市智能消防决策平台设计

开发软件&#xff1a;Eclipse,可以用idea,mysql数据库 开发技术&#xff1a;SpringMVC,Spring,Hibernate,jquery,layui 本系统的功能主要分为两个角色&#xff0c;其中用户的功能有&#xff1a;登陆注册&#xff0c;查看火灾案例&#xff0c;火警报警&#xff0c;查看自己的报警…

【产品经理必备文档】述职报告/年终总结汇报ppt模板

今天和大家免费分享产品必备文档模板——产品经理述职文档&#xff08;年终总结汇报&#xff09;的ppt模板~~~ 【文档下载】 这个ppt模板可以在下方小程序里免费下载哦 【编写教程】 个人工作年终总结一般分成4部门&#xff1a;个人岗位职责、工作完成情况、年度经验总结、 1…

北语、北外2022年12月公派英语统考的通知

近日&#xff0c;北语和北外均发布了12月29日国家公派英语高级班结业统考的通知。与以往不同的是&#xff1a;为无法参加12月29日统考的学员增加一次考试机会&#xff0c;时间定于2023年2月25日&#xff0c;但需要提前报名。具体报名时间及方式参见两校的通知&#xff0c;知识人…

17_ 数据库 _ MySQL主从同步配置

文章目录一、主从同步的定义二、使用主从同步的好处三、主从同步的机制四、配置主从同步的基本步骤五、详细配置主从同步的方法5.1 备份主服务器原有数据到从服务器5.1.1 主服务器Ubuntu上进行备份5.1.2 在从服务器Windows上进行数据还原5.2 配置主服务器master&#xff08;Ubu…

单商户商城系统功能拆解48—应用中心—消息通知

单商户商城系统&#xff0c;也称为B2C自营电商模式单店商城系统。可以快速帮助个人、机构和企业搭建自己的私域交易线上商城。 单商户商城系统完美契合私域流量变现闭环交易使用。通常拥有丰富的营销玩法&#xff0c;例如拼团&#xff0c;秒杀&#xff0c;砍价&#xff0c;包邮…

JUC(九)-线程池-认识JDK中的线程池

JUC、线程池相关内容 文章目录JUC、线程池相关内容一、 什么是线程池1.1 为什么要使用线程池二、 JDK 自带的线程池2.1 newFixedThreadPool方法2.2 newSingleThreadPool方法2.3 newCachedTreadPool方法2.4 newScheduleTreadPool方法2.4.5 Executors Demo2.5 newWorkStealingTre…

搞机器学习不会线性代数?那怎么行

搞机器学习不会线性代数&#xff1f;那怎么行&#xff01; 文章目录搞机器学习不会线性代数&#xff1f;那怎么行&#xff01;1 直观真正理解向量2 理解向量的加法与数乘3 理解向量乘法的本质3.1 向量内积3.2 向量外积4 理解基向量与线性无关4.1 如何理解基向量4.2 如何理解线性…

刷完了这份足足485页的“1000道Java工程师面经”,成功上岸!

前言 本人18年毕业于一家普通二本&#xff0c;考研凉了且没有实习经验&#xff0c;只做过两个项目会一点SpringBoot&#xff0c;每天就是不断地投简历、刷面经&#xff0c;感觉自己都要抑郁了 最后勉强进入了一家学校合作的外包公司干了3年的CRUD&#xff0c;刚开始每个月拿着…

当一个人学习编程之后,带来的人生有什么新变化?

数字化迅速蔓延的世界里&#xff0c;拥有技术技能&#xff08;特别是编程技能&#xff09;可以为你提供更多更好的个人发展机会。在这里&#xff0c;两位半路转行的程序员给你解释了为什么任何人都应该学习编写代码。因为&#xff0c;学习编程既然改变了他们的生活&#xff0c;…

Transformers学习笔记2. HuggingFace数据集Datasets

Transformers学习笔记2. HuggingFace数据集Datasets一、简介二、操作1. 下载数据集2. 常用函数&#xff08;1&#xff09;排序&#xff08;2&#xff09;打乱顺序&#xff08;3&#xff09;选择函数&#xff08;4&#xff09;过滤&#xff08;5&#xff09;切分数据集&#xff…

图书管理网站

开发工具(eclipse/idea/vscode等)&#xff1a; 数据库(sqlite/mysql/sqlserver等)&#xff1a; 功能模块(请用文字描述&#xff0c;至少200字)&#xff1a; 模块划分&#xff1a;老师模块、班级模块、学生模块、课程模块、试题模块、试卷模块、 组卷模块、考试模块、答题模块 管…

第十五章项目1——水果管理系统

文章目录目的从需求开始出发从数据库和数据库连接开始——DAO层对应数据库和数据表的创建项目优化——Mybatis等框架思路引入关于Servlet的编写项目优化——MVC思路引入项目优化——ViewBaseServlet模板引擎的引入项目优化——dispatcherServlet引入项目优化——Service层引入项…

【图像去噪】即插即用法图像去噪【含Matlab源码 152期】

⛄一、简介 理论知识参考文献&#xff1a;基于Retinex和ADMM优化的水下光照不均匀图像增强算法 ⛄二、部分源代码 function out PlugPlayADMM_deblur(y,h,lambda,method,opts) %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% %out PlugPlayADMM_deblur(y,h,lambda,method,opt…

19-Mysql执行原理之索引合并详解

Mysql执行原理之索引合并详解 我们前边说过MySQL在一般情况下执行一个查询时最多只会用到单个二级索引&#xff0c;但存在有特殊情况&#xff0c;在这些特殊情况下也可能在一个查询中使用到多个二级索引&#xff0c;MySQL中这种使用到多个索引来完成一次查询的执行方法称之为&…

day24【代码随想录】平衡二叉树、二叉树的所有路径、路径总和||、路径总和、求根节点到叶节点数字之和

文章目录前言一、平衡二叉树&#xff08;力扣110&#xff09;二、二叉树的所有路径&#xff08;力扣257&#xff09;1、递归法2、迭代法三、路径总和 II&#xff08;力扣113&#xff09;四、路径总和&#xff08;力扣112&#xff09;五、求根节点到叶节点数字之和&#xff08;力…