设计模式(二)工厂模式:2-工厂方法模式
模拟场景:
继续沿用在简单工厂模式中讨论的,运算器相关的场景。
思想:
考虑之前最初的设计,简单工厂模式中,最大的问题在于,面对新增的需要在工厂中创建的对象,对其的修改会违反开闭原则。
工厂方法模式(Factory Method)对于这种问题的解决方案是:将生产运算器的工厂抽象出来(AbsOperationFactory),然后为原来每一个需要创建的对象(继承AbsOperation),都建立一个专门的工厂。这样一来,可以巧妙地利用多态的性质,完成代码的解耦。
由此可见,工厂方法模式,是模板方法模式(Template Method)的一种典型应用,模板方法模式会在之后细讲。
所以说,一个完整的工厂方法模式,除了客户端(Client)之外,还包括以下4个内容:
- 抽象工厂(Abstract Factory)
- 具体工厂(Concrete Factory)
- 抽象产品(Abstract Product)
- 具体产品(Concrete Product)
UML:
1 @Test 2 public void test() { 3 double[] vals1 = { 1, 2, 3, 4, 5, 6, 7, 8, 9 }; 4 OperationAddFactory factory = new OperationAddFactory(); 5 OperationAdd operator = factory.createOperation(); 6 Assert.assertTrue(operator.calc(vals1) - 45 == 0); 7 }JUnit
工厂方法模式的最大优势在于:
- 客户端可以自由决定调用的方式。
- 产品的变化,不会影响客户端的调用。
总结:
工厂方法模式面对产品的扩张,需要增加一个产品类和一个产品工厂类。这么做虽然解耦了,当时带来了更多的工作量。
与简单工厂模式相比,工厂方法模式通过多态的运用,保证了开闭原则,但是这是通过多构造一个实例工厂的方式来完成的,这意味着近乎一倍的内存开销,所以在使用这种模式时,工厂内部负责创建的对象,不宜过多,否则得不偿失。
与简单工厂模式的反射优化相比,工厂方法模式,几乎没有任何优势。工厂方法模式能做到的,简单工厂模式的反射优化,基本都能够做到,还少一倍的内存开销。要说优势,也就是通过 new 关键字正向创建对象,比反射的 newInstance() 方法速度更快,而且能在编译阶段发现错误。
所以说,在我看来,工厂方法模式最大的意义,是为其扩展出去的抽象工厂模式(Abstract Factory)铺垫。而实际的应用,简单工厂模式的反射更具优势。
- 设计模式之工厂设计模式(一:简单工厂模式与工厂方法模式)
- Head First 设计模式学习——简单工厂方法-工厂方法模式-抽象工厂模式
- JAVA设计模式(01):创建型-工厂模式【工厂方法模式】(Factory Method)
- JAVA设计模式之:工厂模式(上)--工厂方法模式
- Java设计模式(三):工厂模式(简单工厂模式、工厂方法模式、抽象工厂模式)
- 设计模式: 自己手动写一个工厂模式(整合工厂方法模式和抽象工厂模式)
- iOS应用设计模式开发中对简单工厂和工厂方法模式的运用
- 简单工厂模式、工厂方法模式和抽象工厂模式-设计模式学习
- Php设计模式之工厂模式(二)【工厂方法模式 Factory Method】
- Java设计模式(一) 设计模式初探——简单工厂和工厂方法模式
- 设计模式入门学习之工厂模式(工厂方法模式)
- 设计模式之工厂方法模式VS简单工厂方法模式
- PHP设计模式-工厂系列(二)-工厂方法模式
- 设计模式(2)工厂模式、工厂方法模式、抽象工厂模式
- 设计模式之简单工厂、工厂方法模式、抽象工厂模式
- 设计模式之简单工厂方法模式和工厂方法模式
- 设计模式- 简单工厂模式---->工厂方法模式---->抽象工厂模式
- 设计模式:工厂方法模式(C++)【简单工厂进行升级】
- 常用Java设计模式系列(5)- 简单工厂、工厂方法模式和抽象工厂模式
- 工厂设计模式(二)--工厂方法模式