IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> Java知识库 -> 每日一学 - Java设计模式(Day9)——工厂模式 -> 正文阅读

[Java知识库]每日一学 - Java设计模式(Day9)——工厂模式

工厂模式(Factory Pattern)是 Java 中最常用的设计模式之一。这种类型的设计模式属于创建型模式,它提供了一种创建对象的最佳方式。在工厂模式中,我们在创建对象时不会对客户端暴露创建逻辑。工厂模式一般分为三种:简单工厂模式工厂方法模式抽象工厂模式

在这里简单说一下,本篇博客不仅仅是工厂模式,其中涉及到一些在学习工厂模式的时候所产生的一些疑问也给记录了下来。

一、为什么要有工厂模式

学习设计模式,往往有时候会想不通,我明明可以简单的实现,为什么还要搞的这么复杂,设计模式是一种设计思想,他的出现往往是多方面考虑,写代码不只是为完成功能,更多的需要考虑完成功能的基础之上日后维护起来怎么方便,要学会提升自己,而不是天天CRUD。

为什么要有工厂模式,工厂模式存在的意义是什么?我需要创建哪个对象直接new不就可以了吗,我相信一般学习工厂模式的前奏都会考虑这些,其实我也是。

我们以类Sample为例, 如果我们要创建Sample的实例对象:

Sample sample=new Sample();

可是,实际情况是,通常我们都要在创建sample实例时做点初始化的工作,比如赋值 查询数据库等。

首先,我们想到的是,可以使用Sample的构造函数,这样生成实例就写成:

Sample sample=new Sample(参数);

场景一:如果创建sample实例时所做的初始化工作不是像赋值这样简单的事,可能是很长一段代码,如果也写入构造函数中,那你的代码很难看了。

初始化工作如果是很长一段代码,说明要做的工作很多,将很多工作装入一个方法中,相当于将很多鸡蛋放在一个篮子里,是很危险的,这也是有悖于Java面向对象的原则。

面向对象的封装(Encapsulation)和分派(Delegation)告诉我们,尽量将长的代码分派“切割”成每段,将每段再“封装”起来(减少段和段之间耦合联系性),这样,就会将风险分散,以后如果需要修改,只要更改每段,不会再发生牵一动百的事情。

在本例中,首先,我们需要将创建实例的工作使用实例的工作分开, 也就是说,让创建实例所需要的大量初始化工作从Sample的构造函数中分离出去。这时我们就需要Factory工厂模式来生成对象了,不能再用上面简单new Sample(参数)

场景二:还有,如果Sample有个继承如MySample, 按照面向接口编程,我们需要将Sample抽象成一个接口.Sample是接口,有两个子类MySample 和HisSample .我们要实例化他们时,如下:

ISample mysample=new MySample();
ISample hissample=new HisSample();

随着项目的深入,Sample可能还会"生出很多儿子出来", 那么我们要对这些儿子一个个实例化,更糟糕的是,可能还要对以前的代码进行修改:加入后来生出儿子的实例.这在传统程序中是无法避免的.但如果你一开始就有意识使用了工厂模式,这些麻烦就没有了.

二、简单工厂模式

简单工厂模式不是23种里的一种,简而言之,就是有一个专门生产某个产品的类。

建立一个专门生产Sample实例的工厂:

public class Factory {
    public static ISample creator(int which) {
        if (which == 1)
            // 此处创建对象并不会这么简单,不然也不会用工厂。。。
            return new MySample();
        else if (which == 2)
            return new HisSample();
        return null;
    }
}

interface ISample {

}

class MySample implements ISample {

}

class HisSample implements ISample {

}

那么在你的程序中,如果要创建ISample的实列时候可以使用

ISample sampleA=Factory.creator(1);

这样,在整个程序层面就不涉及到ISample的具体的实现类,我们只跟接口或者抽象类打交道,达到封装效果,也就减少错误修改的机会。

这个原理可以用很通俗的话来比喻:就是具体事情做得越多,越容易犯错误.这每个做过具体工作的人都深有体会,相反,官做得越高,说出的话越抽象越笼统,犯错误可能性就越少.好象我们从编程序中也能悟出人生道理。

使用工厂方法 要注意几个角色:

  1. 定义产品接口,如上面的Sample类的接口
  2. 产品接口下有ISample接口的实现类,如SampleA,
  3. 其次要有一个Factory类,用来生成产品ISample接口的具体实例。

三、工厂方法模式

工厂模式也就是鼠标工厂是个父类,有生产鼠标这个接口。
戴尔鼠标工厂,惠普鼠标工厂继承它,可以分别生产戴尔鼠标,惠普鼠标。
生产哪种鼠标不再由参数决定,而是创建鼠标工厂时决定。
假如创建戴尔鼠标工厂。后续直接调用鼠标工厂.生产鼠标()即可。在这里插入图片描述

四、抽象工厂模式

抽象工厂模式也就是不仅生产鼠标,同时生产键盘。
也就是PC厂商是个父类,有生产鼠标,生产键盘两个接口。
戴尔工厂,惠普工厂继承它,可以分别生产戴尔鼠标+戴尔键盘,和惠普鼠标+惠普键盘。
假如创建戴尔鼠标工厂。 后续工厂.生产鼠标()则生产戴尔鼠标,工厂.生产键盘()则生产戴尔键盘。
在这里插入图片描述
假设我们增加耳麦这个产品,则首先我们需要增加耳麦这个父类,再加上戴尔耳麦,惠普耳麦这两个子类。

之后在PC厂商这个父类中,增加生产耳麦的接口。最后在戴尔工厂,惠普工厂这两个类中,分别实现生产戴尔耳麦,惠普耳麦的功能。

在这里插入图片描述

五、工厂方法模式和抽象工厂区别

抽象工厂模式把产品进行了两个纬度的划分,其中一个纬度是从产品本身派生出来的,鼠标、键盘、麦克风这些产品类别的划分。另外一个纬度是从工厂派生出来的,有不同品牌的工厂。

而工厂方法模式只有一个纬度,产品和工厂是完全对应的。

  Java知识库 最新文章
计算距离春节还有多长时间
系统开发系列 之WebService(spring框架+ma
springBoot+Cache(自定义有效时间配置)
SpringBoot整合mybatis实现增删改查、分页查
spring教程
SpringBoot+Vue实现美食交流网站的设计与实
虚拟机内存结构以及虚拟机中销毁和新建对象
SpringMVC---原理
小李同学: Java如何按多个字段分组
打印票据--java
上一篇文章      下一篇文章      查看所有文章
加:2022-03-04 15:22:29  更:2022-03-04 15:24:28 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/24 11:13:13-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码