工厂模式分为简单工厂模式,工厂方法模式,抽象工厂模式。属于创建型模式
**
简介:平常创建对象都是直接new对象,如果创建对象需要关联一系列操作,我们一般会在构造方法里关联这些操作;但是操作比较多、复杂,会使得构造方法很长降低可读性。这时不妨创建一个工厂类专门负责对象的创建;
工厂模式的基本逻辑
假设我们的业务代码当中,有一个被广泛引用的“口罩类”,这个类实例需要在许多地方被创建和初始化,而初始化的代码也比较复杂
public class Mask { //口罩类public Mask(){ //构造方法//.... // 100行初始化代码}}
针对这种情况,我们可以构建一个“口罩工厂”专门负责创建口罩对象,把口罩类的初始化代码迁移到工厂类的创建方法当中:
public class MaskFactory { //口罩工厂public Mask createMask() { //返回口罩类对象的方法Mask mask = new Mask();// .....// 100行初始化代码return mask;}}
简单工厂模式
简单工厂模式有唯一的工厂类,工厂类的创建方法根据传入的参数做if-else条件判断,决定最终创建什么样的产品对象。
工厂类创建对象,工厂类根据传入参数决定具体子类对象
接上,假如口罩类更加复杂(存在子类),我们可以给工厂类创建对象加上一系列条件判断
假设口罩类分为2个子类。分别是高端口罩和低端口罩,我们可以把口罩类Mask转变为接口
public interface Mask {void show();}public class HighEndMask implements Mask {@Overridepublic void show() {System.out.println("我是高端口罩");}}public class LowEndMask implements Mask {@Overridepublic void show(){System.out.println("我的低端口罩");}}
在口罩工厂的创建方法中传入参数(这里的参数是type),根据参数来做条件判断,决定创建什么样的口罩:
public class MaskFactory{public Mask createMask(String type) {Mask mask = null;if("高端口罩".equals(type)){mask = new HighEndMask();// 高端口罩HighEndMask的100行初始化代码}else if("低端口罩".equals(type)){mask = new LowEndMask();// 低端口罩LowEndMask的100行初始化代码}return mask;}}
**
工厂方法模式
接上简单工厂模式,如果需要增加新的类型的口罩。就需要增加新的if-else条件判断。不符合面向对象的开放-封闭原则。
要避免“修改原有代码增加新的条件判断”,可以为每一个口罩子类创建相应的口罩工厂。 工厂子类分别实现抽象的工厂方法
所谓的开放-封闭原则,就是在面向对象程序中对“扩展”开放,对“修改”封闭。如果每次业务改动都要对旧有代码修改,不但容易出错,可读性也不好。
(即便没有更改一个类的原有代码,只是增加新的方法,之类的也算是破坏了封闭原则)
修改的代码
public interface MaskFactory {Mask createMask();}public class HighEndFactory implements MaskFactory{@Overridepublic Mask createMask() {Mask mask = new HighEndMask();// HighEndMask的100行初始化代码return mask;}}public class LowEndFactory implements MaskFactory{@Overridepublic Mask createMask() {Mask mask = new LowEndMask();// LowEndMask的100行初始化代码return mask;}}
Test代码
public class Test {public static void main(String[] args) {MaskFactory factoryA = new LowEndFactory();MaskFactory factoryB = new HighEndFactory();Mask maskA = factoryA.createMask();Mask maskB = factoryB.createMask();maskA.show();maskB.show();}}
抽象工厂模式
本质:**把产品类从另外一种分类方式分组,实现不同产品对应同一工厂类的不同方法
如果需要创建的子类越来越多,不只有口罩类,还有防毒面具,防护服之类的,按照上面的办法每一种子类都要有一个对应的工厂类。显然太繁琐,这时抽象工厂模式可以解决**
假设业务中需要创建口罩、防毒面具、防护服这三种产品,而每一种产品有包含高端和低端两类,按照工厂方法模式的解决方案,需要创建的类如下:

转化为以下分类
如果待创建的产品非常多,可以从另外一种角度对产品进行分组,** 比如直接分为高端产品组和低端产品组,就由很多种产品转为只有2种产品(高端-低端)

public interface Mask {void showMask();}public class LowEndMask implements Mask {@Overridepublic void showMask(){System.out.println("我的低端口罩");}}public class HighEndMask implements Mask {@Overridepublic void showMask() {System.out.println("我是高端口罩");}}public interface ProtectiveSuit { //防护服接口void showSuit();}public class LowEndProtectiveSuit implements ProtectiveSuit {@Overridepublic void showSuit() {System.out.println("我是低端防护服");}}public class HighEndProtectiveSuit implements ProtectiveSuit {@Overridepublic void showSuit() {System.out.println("我是高端防护服");}}//工厂类:另外一种分组方式public interface Factory {//创建口罩Mask createMask();//创建防护服ProtectiveSuit createSuit();}public class LowEndFactory implements Factory {@Overridepublic Mask createMask() {Mask mask = new LowEndMask();// LowEndMask的100行初始化代码return mask;}@Overridepublic ProtectiveSuit createSuit() {ProtectiveSuit suit = new LowEndProtectiveSuit();// LowEndProtectiveSuit的100行初始化代码return suit;}}public class HighEndFactory implements Factory {@Overridepublic Mask createMask() {Mask mask = new HighEndMask();// HighEndMask的100行初始化代码return mask;}@Overridepublic ProtectiveSuit createSuit() {ProtectiveSuit suit = new HighEndProtectiveSuit();// HighEndProtectiveSuit的100行初始化代码return suit;}}//Test代码:通过实例化不同的工厂子类,调用不同的创建方法,可以创建出不同的产品:public class Test {public static void main(String[] args) {Factory factoryA = new LowEndFactory();Factory factoryB = new HighEndFactory();//创建低端口罩Mask maskA = factoryA.createMask();//创建高端口罩Mask maskB = factoryB.createMask();//创建低端防护服ProtectiveSuit suitA = factoryA.createSuit();//创建高端防护服ProtectiveSuit suitB = factoryB.createSuit();maskA.showMask();maskB.showMask();suitA.showSuit();suitB.showSuit();}}
简单工厂模式,工厂方法模式的Test也是类似的
总结
- 简单工厂模式:
简单工厂模式有唯一的工厂类,工厂类的创建方法根据传入的参数做if-else条件判断,决定最终创建什么样的产品对象。
- 工厂方法模式:
工厂方法模式由多个工厂类实现工厂接口,利用多态来创建不同的产品对象,从而避免了冗长的if-else条件判断。**
- 抽象工厂模式:
抽象工厂模式把产品子类进行分组,同组中的不同产品由同一个工厂子类的不同方法负责创建,从而减少了工厂子类的数量。
抽象工厂模式把产品子类进行分组,同组中的不同产品由同一个工厂子类的不同方法负责创建,从而减少了工厂子类的数量。




熟悉spring框架的小伙伴,一定知道spring的一个重要特性:依赖注入(DI)。
通过spring的依赖注入,开发人员不需要在业务代码中手动实例化bean对象,也不需要知道任何工厂类。
bean对象从创建到销毁的整个过程,完全交给spring容器来管理,用户需要做的仅仅是在xml配置文件中(或使用注解)设置bean的各项属性:
<bean id="userController" class="com.xiaohui.controller.UserController"><constructor-arg name="userService" ref="userService"></constructor-arg></bean><bean id="userService" class="com.xiaohui.service.UserService">
根据上面的配置,spring容器会动态创建UserController对象,并创建UserController所依赖的UserService对象。
如果开发人员希望把userService这个bean对象的实现类换成另一个类,并不需要改动任何代码,只需要修改配置文件中对应bean的class属性即可。
spring通过反射
在大多数情况下,我们使用new关键字创建对象,对象所属的class是在代码中明确定义好的。
但是在少数情况下,我们需要借助class的元信息(比如完整类名),在程序运行期间动态创建对象,这就用到了Java的反射。
当我们在spring配置文件中配置了相应的bean,启动项目,spring会为我们解析xml配置文件,并根据bean的不同生命周期,由spring内部的“工厂”创建出bean对象。
对spring依赖注入原理有兴趣的小伙伴,可以阅读spring源码中的BeanFactory接口,以及相关的实现类。
