工厂设计模式

一、简介

都不知道简介要写什么,工厂模式嘛,就是工厂嘛,生产东西的嘛……
在Java里面就是用来帮助我们生产对象的咯~~
主要作用嘛,大概就是将创建和使用对象拆分减低耦合度吧。

二、分类

分类的话,大致可以分成3种

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

这里有一件比较有意思的是,简单工厂是不包含在gof23种设计模式里面的,据说是因为过于简单了,hhhh。

三、简单工厂

简单工厂模式算是3种工厂模式中最基础最简单的了,用的也是最多的。
简单工厂模式具体的思路是这样的:

提供一个抽象基类以及若干具体的子类,提供一个工厂和一个客户端
通常情况下根据需求创建对象的逻辑都是由客户端去完成的,这里客户端指的是创建和使用对象的类,因为不知道怎么叫就叫客户端吧
而工厂的作用就是使用一个工厂类将创建对象这一部分拆分出来交给工厂,客户端只负责从工厂拿到对象然后去使用对象的功能
工厂返回的对象也是抽象基类类型,具体实现是的什么子类是由工厂来决定的(动态绑定)
我们在想要使用简单工厂模式的时候,只需要分清楚三个角色:工厂、基类、子类就可以了

下面是简单工厂模式的类图

下面是代码示例,大概讲一下示例的流程背景

假设我们有一家饼干店类(用来卖饼干的),有若干个饼干类(饼干),每次卖饼干的时候都要根据条件创建不同的饼干类型,每次多出一个饼干类的时候我们都要修改饼干店的源代码,现在我们希望使用工厂模式来拆分饼干店的职责(你就负责卖,别的不需要你操心),将创建饼干对象(new 对象)的这一部分交给一个工厂来处理,工厂处理好后直接返回饼干(对象)供饼干店使用

那下面的代码就产生了:

/*** @author ZhongJing </p>* @Description 饼干抽象类 </p>*/
public abstract class BaseBiscuits {/*** 描述饼干的制作过程* 抽象方法,让具体的饼干子类来重写*/public abstract void makeBiscuits();}/*** @author ZhongJing </p>* @Description 曲奇饼干 </p>*/
public class Cookies extends BaseBiscuits{@Overridepublic void makeBiscuits() {System.out.println("曲奇饼干制作完成……");}
}/*** @author ZhongJing </p>* @Description 夹心饼干 </p>*/
public class SandwichBiscuits extends BaseBiscuits {@Overridepublic void makeBiscuits() {System.out.println("夹心饼干制作完成……");}
}/*** @author ZhongJing </p>* @Description 饼干工厂类 </p>*/
public class BiscuitsFactory {/*** 静态方法,根据传入的饼干类型创建不同的饼干* @param biscuitsType 饼干类型* @return 饼干的具体对象*/public static BaseBiscuits createBiscuits(String biscuitsType) {BaseBiscuits biscuits = null;if ("cookies".equalsIgnoreCase(biscuitsType)) {biscuits = new Cookies();} else if ("sandwich".equalsIgnoreCase(biscuitsType)) {biscuits = new SandwichBiscuits();} else {System.out.println("不存在该类型的饼干,类型:" + biscuitsType);}return biscuits;}}/*** @author ZhongJing </p>* @Description 饼干店(客户端) </p>*/
public class BiscuitsStore {public static void main(String[] args) {String type1 = "cookies";String type2 = "sandwich";BaseBiscuits biscuits = BiscuitsFactory.createBiscuits(type1);biscuits.makeBiscuits();BaseBiscuits biscuits2 = BiscuitsFactory.createBiscuits(type2);biscuits2.makeBiscuits();}}

四、工厂方法

在了解了简单工厂以后,心里总会有一个疑问,把创建对象交给工厂对于调用的类来说确实是方便了,也降低了耦合度,也不用一直修改了,但是工厂和类之间的耦合度不是依旧很高嘛,而且如果每新增一个基类就要修改一次工厂的代码,依旧是一件很麻烦的事情,有没有一种办法,可以只新增而不修改旧的代码呢?
有,就是工厂方法。

工厂方法模式(Factory Method Pattern):定义一个用于创建对象的接口,让子类决定将哪一个类实例化。工厂方法模式让一个类的实例化延迟到其子类。工厂方法模式又简称为工厂模式(Factory Pattern),又可称作虚拟构造器模式(Virtual Constructor Pattern)或多态工厂模式(Polymorphic Factory Pattern)。工厂方法模式是一种类创建型模式。

大概的类图就是下面这样的,和简单工厂基本一样,只不过创建对象由子类来完成了,基类工厂只提供方法.
这样做的好处就在于,不管产品的子类如何新增或者改变,都可以通过修改或者新增子类工厂的方式来解决问题。

当然,工厂方法也是有坏处的。
当我们的产品子类新增是,往往伴随着子类工厂的新增,如果持续下去就会发生类爆炸,增加系统的负荷。
所以也不是什么地方都可以使用的,工厂方法一般都适用于框架上游,在编写时我根本不知道到底会有什么子类,我只需要定义方法和返回的基类,具体的实现将会由整合的框架下游或者开发人员来实现,也算是一种规范的制定吧。

现在我们将之前的简单工厂修改一下,变成工厂方法,代码如下

/*** @author ZhongJing </p>* @Description 饼干抽象类 </p>*/
public abstract class BaseBiscuits {/*** 描述饼干的制作过程* 抽象方法,让具体的饼干子类来重写*/public abstract void makeBiscuits();}/*** @author ZhongJing </p>* @Description 曲奇饼干 </p>*/
public class Cookies extends BaseBiscuits {@Overridepublic void makeBiscuits() {System.out.println("曲奇饼干制作完成……");}
}/*** @author ZhongJing </p>* @Description 夹心饼干 </p>*/
public class SandwichBiscuits extends BaseBiscuits {@Overridepublic void makeBiscuits() {System.out.println("夹心饼干制作完成……");}
}/*** @author ZhongJing </p>* @Description 工厂基类 </p>*/
public abstract class BaseBiscuitsFactory {/*** 只提供创建饼干对象的方法,具体创建哪种饼干由子类来决定*/public abstract BaseBiscuits createBiscuits();}/*** @author ZhongJing </p>* @Description 创建曲奇饼干的工厂 </p>*/
public class CookiesFactory extends BaseBiscuitsFactory{@Overridepublic BaseBiscuits createBiscuits() {return new Cookies();}
}/*** @author ZhongJing </p>* @Description 创建夹心饼干的工厂 </p>*/
public class SandwichBiscuitsFactory extends BaseBiscuitsFactory{@Overridepublic BaseBiscuits createBiscuits() {return new SandwichBiscuits();}
}/*** @author ZhongJing </p>* @Description 饼干店(客户端) </p>*/
public class BiscuitsStore {public static void main(String[] args) {BaseBiscuits cookies = createBiscuits(new CookiesFactory());cookies.makeBiscuits();BaseBiscuits sandwichBiscuits = createBiscuits(new SandwichBiscuitsFactory());sandwichBiscuits.makeBiscuits();}public static BaseBiscuits createBiscuits(BaseBiscuitsFactory factory) {return factory.createBiscuits();}}

五、抽象工厂

概述:

抽象工厂提供一个接口以创建一系列相关或相互依赖的对象,而无需指定它们具体的类

抽象工厂目的其实就是根据不同的分类创造出一个对象族,在我看来简单工厂、工厂方法、抽象工厂就像是一个递推逐渐复杂化的过程,其实本质的原则都是一样的,只不过相对于工厂方法,抽象工厂不再是只创建一种对象,而是直接创建一个族群的对象而已。

抽象工厂的角色依旧分为抽象工厂、具体工厂、抽象产品、具体产品四种角色。
他的UML类图大概是这样的

现在我们来修改一下之前饼干店的例子,假设现在我们饼干店越做越大,开了一家分店,就叫分店B吧,我们同时拥有了两家店,用户也有了更多的选择,因为是连锁店,饼干的类型依旧是原来的类型但是口感存在着差异,有的客户喜欢吃A店的,而有的客户又喜欢吃B店的,这种情况下一个单一的工厂已经解决不了我们现存的问题了,就需要我们使用抽象工厂来进行分类,A店的所有饼干就相当于一个对象族、B店的所有饼干是另外一个对象族

下面通过代码来实现一下我们的需求:

/*** @author ZhongJing </p>* @Description 曲奇抽象类 </p>*/
public abstract class BaseCookies {/*** 描述制作曲奇饼干的流程*/public abstract void makeCookies();}/*** @author ZhongJing </p>* @Description 夹心饼干抽象类 </p>*/
public abstract class BaseSandwich {/*** 描述夹心饼干的制作过程*/public abstract void makeSandwich();}/*** @author ZhongJing </p>* @Description A店的曲奇饼干(具体类) </p>*/
public class CookiesA extends BaseCookies{@Overridepublic void makeCookies() {System.out.println("A店曲奇饼干制作完成……");}
}/*** @author ZhongJing </p>* @Description B店的曲奇饼干(具体类) </p>*/
public class CookiesB extends BaseCookies{@Overridepublic void makeCookies() {System.out.println("B店曲奇饼干制作完成……");}
}/*** @author ZhongJing </p>* @Description A店的夹心饼干(具体类) </p>*/
public class SandwichA extends BaseSandwich{@Overridepublic void makeSandwich() {System.out.println("A店夹心饼干制作完成……");}
}/*** @author ZhongJing </p>* @Description B店的夹心饼干(具体类) </p>*/
public class SandwichB extends BaseSandwich {@Overridepublic void makeSandwich() {System.out.println("B店夹心饼干制作完成……");}
}/*** @author ZhongJing </p>* @Description 抽象工厂类 </p>*/
public abstract class BaseBiscuitsFactory {/*** 制作曲奇饼干*/public abstract BaseCookies createCookies();/*** 制作夹心饼干*/public abstract BaseSandwich createSandwich();}/*** @author ZhongJing </p>* @Description A店工厂实现类 </p>*/
public class BiscuitsFactoryA extends BaseBiscuitsFactory{@Overridepublic BaseCookies createCookies() {return new CookiesA();}@Overridepublic BaseSandwich createSandwich() {return new SandwichA();}
}/*** @author ZhongJing </p>* @Description B店工厂实现类 </p>*/
public class BiscuitsFactoryB extends BaseBiscuitsFactory {@Overridepublic BaseCookies createCookies() {return new CookiesB();}@Overridepublic BaseSandwich createSandwich() {return new SandwichB();}
}/*** @author ZhongJing </p>* @Description 客户端 </p>*/
public class Client {public static void main(String[] args) {BaseCookies cookies = null;BaseSandwich sandwich = null;BaseBiscuitsFactory factory = null;// 想吃A店的饼干factory = new BiscuitsFactoryA();cookies = factory.createCookies();sandwich = factory.createSandwich();cookies.makeCookies();sandwich.makeSandwich();// 想吃B店的饼干factory = new BiscuitsFactoryB();cookies = factory.createCookies();sandwich = factory.createSandwich();cookies.makeCookies();sandwich.makeSandwich();}}

相信到这里也可以看出这样做的好处了吧,这样做的好处就是就算我们现在有了C店、D店、E店等更多的分店,也只需要新增饼干的具体子类和工厂的具体子类就可以了,在我们调用时依旧还是使用饼干的基类和工厂的基类,请不要在意我的客户端使用new工厂子类的方式,我只是懒得写了,在真实的应用中我们根本不需要关系究竟是哪一个子类实现了我们的方法,只需要对其抽象定义和调用就好了,具体的实现在运行时才会确定下来。

Java设计模式——工厂设计模式相关推荐

  1. java二十三种设计模式——工厂设计模式

    java设计模式的分类 在java中,设计模式有三十三种之多,分为三大类: 创建性模式,共五种:工厂方法模式.抽象工厂模式.单例模式.建造者模式.原型模式. 结构性模式,共七种:适配器模式.装饰器模式 ...

  2. 创建设计模式 - 工厂设计模式

    创建设计模式 - 工厂设计模式 欢迎到工厂设计模式在Java教程.Factory Pattern是Creational Design模式之一,它在JDK以及Spring和Struts等框架中得到广泛应 ...

  3. Java之工厂设计模式

    工厂设计模式 简单工厂模式 工厂方法模式 抽象工厂模式 简单工厂模式-Spring-beanfactory 简单工厂模式:专门定义一个类用来创建其他类的实例,被创建的实例通常拥有共同的父类. 组成: ...

  4. java 生产设计模式_java设计模式-工厂设计模式

    工厂设计模式是创建型设计模式,有三种设计方法:简单工厂(产品父类),工厂模式(工厂父类),抽象工厂(父类接口) 一.简单工厂 简单工厂的设计思想是: 1.定义一个产品的父类 2.具体产品类继承父类 3 ...

  5. Java设计模式-工厂设计模式

    工厂设计模式概念 工厂模式是我们最常用的实例化对象模式了,是用工厂方法代替new操作的一种模式.著名的Jive论坛 ,就大量使用了工厂模式,工厂模式在Java程序系统可以说是随处可见.因为工厂模式就相 ...

  6. 设计模式:工厂设计模式

    通过工厂设计模式可降低代码的耦合度.耦合度太高会导致代码不方便维护 就相当于A一直要与B绑定在一起.可以完全参考Java虚拟机的设计思想 程序→JVM→适应不同的操作系统(A->C->B) ...

  7. 设计模式—工厂设计模式

    工厂设计模式 1.概述 2.简单工厂模式 2.1 结构 2.2 实现 2.3 优缺点 2.4 扩展 3.工厂方法模式 3.1 概述 3.2 结构 3.3 实现 3.4 优缺点 4.抽象工厂模式 4.1 ...

  8. php设计模式-工厂设计模式

    概念: 工厂设计模式提供获取某个对象的新实例的一个接口,同时使调用代码避免确定实际实例化基类步骤. 很多高级模式都是依赖于工厂模式. 转载于:https://www.cnblogs.com/sjhss ...

  9. 嵌入式C设计模式---工厂设计模式

    更新记录链接:嵌入式C设计模式---前言_嵌入式学习_force的博客-CSDN博客_嵌入式前言 目录         1.工厂设计模式动漫详解         2.智慧温室大棚监控系统项目详解工厂应 ...

最新文章

  1. solr异常--Expected mime type application/octet-stream but got text/html.
  2. spring 注释_Spring核心注释
  3. OpenShift 4 之 GitOps(2)用ArgoCD部署应用
  4. TypeScript + Gulp + 混淆 + 打包
  5. 如何用Baas快速在腾讯云上开发小程序-系列3 :实现腾讯云COS API调用
  6. jasoncpp读取jason数据如何判断某一字段是否存在
  7. TI 杯2019年全国大学生电子设计竞赛题
  8. java7723魂斗罗2_魂斗罗2013-丛林之谜
  9. java程序员 技术成长路线
  10. Chrome对开发有用的插件
  11. 平江南江计算机培训,平江县南江学区: 假期培训促提升,收心归位再出发
  12. MySQL——基础知识
  13. 智能机器人与智能系统(大连理工大学庄严教授)——3.工业机器人
  14. Unix/Linux编程:getcontext、setcontext
  15. 安徽阜阳育英计算机学校,阜阳育英中学
  16. python音乐的数据抓取与分析_python抓取网易云音乐热评做词图数据分析
  17. 每日力扣009——575. 分糖果(OnO1)
  18. npm install 报错没有匹配版本:No matching version found for
  19. 【UnityShader】云海效果模拟与视差映射
  20. u盘启动识别不到服务器硬盘,u盘启动读不了硬盘,教您U盘装系统找不到硬盘解决方法...

热门文章

  1. Java剑开天门(四)
  2. 【Python游戏】用Python写的地道战小游戏,代码着实有点多 | 附带源码
  3. 疑难杂症:内存明明很富裕,却还是申请不到?
  4. 有关几何画板迭代实现效果方法和注意事项
  5. xshell session导入mobaxsterm
  6. 王道每日一题2022年考研
  7. 包包各部位名称图解_[原创]整理出的包包名称及各部位英语集
  8. phpexcel导入导出(轻量) 淘宝导入
  9. helloworldjava_Java语言入门-第一个HelloWorld程序
  10. 游戏脚本语言KongFuScript