场景
new 对象的替代方案
需要灵活、可扩展的框架时
在异构项目中,从外部产生的对象
测试驱动开发框架下使用。测试驱动开发 -TDD
工厂方法模式 定义 定义一个用于创建对象的接口,让子类决定实例化哪一个类。工厂方法使一个类的实例化延迟到其子类。
抽象产品类Product负责定义产品的共性,实现对事物最抽象的定义; Creator为抽象的创建类,即抽象工厂,具体如何创建产品类是由具体的实现工厂ConcreteCreator完成的。
优点
良好的封装,代码结构清晰,降低模块间的耦合;
良好的扩展性;
屏蔽具体的产品类,只要接口不变,系统中上层模块就不需要发生变化。
高层模块只需要知道产品的抽象类,不关心实现类,符合迪米特法则; 只依赖产品的抽象,符合倒置原则; 使用产品子类替换父类时也没有问题,符合里氏替换原则;
缺点 对于不同类型的产品都要增加不同类型的工厂来管理,增加代码的复杂性
实现 通用实现 产品类:
1 2 3 4 5 6 7 8 9 10 11 12 public abstract class Product { public abstract void method1 () ; public void method2 () {} } public class Product1 extends Product { public void method1 () {} } public class Product2 extends Product { public void method1 () {} }
工厂类:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 public abstract class Factory { public abstract <T extends Product> T create (Class<T> c) ; } public class ConcreteFactory extends Factory { public <T extends Product> T create (Class<T> c) { Product p = null ; try { p = (Product)Class.forName(c.getName()).newInstance(); }catch (Exception e){ } return (T)p; } }
使用:
1 2 Factory factory = new ConcreteFactory(); Product p = factory.createt(Product1.class);
缩小为简单工厂 去掉抽象的Factory类,create()方法变为静态方法即可。
1 2 3 4 5 6 7 8 9 10 11 12 public void Factory{ public static <T extends Product> T create (Class<T> c) { Product p = null ; try { p = (Product)Class.forName(c.getName()).newInstance(); }catch (Exception e){ } return (T)p; } }
调用代码:
1 Product p = Factory.create(Product1.class ) ;
升级为多个工厂类 遇到复杂情况下,一个工厂类初始化需要耗费很多资源,这样可以将工厂类细化拆分。
1 2 3 4 5 6 7 8 9 10 11 12 public class Factory1 extends Factory { public static Product create () { return new Product1(); } } public class Factory2 extends Factory { public static Product create () { return new Product2(); } }
这样的好处是职责清晰,结构简单,但是可扩展性和可维护性差了些。 一般情况下,再增加一个协调类,避免调用者直接与各个子工厂类交流,协调类的作用是封装子工厂类,对高层模块提供统一的访问接口。
替代单例模式 通过反射的方式来创建唯一一个实例
延迟初始化 一个对象被使用完毕后,并不立即释放,工厂类保持其初始状态,等待再次被使用。
延迟加载框架可以被扩展为,限制某个产品类的最大实例化数量(如链接池的最大链接数量)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 public class ProductFactory { private static final Map<String,Product> pMap = new HashMap(); public static synchronized Product createProduct (String type) throws Exception { Product p = null ; if (pMap.containsKey(type)){ p = pMap.get(type); }else { if (type.equals("Product1" )){ p = new Product1(); }else { p = new Product2(); } } return product; } }
定义一个用于创建对象的接口,让子类决定实例化哪一个类。工厂方法使一个类的实例化延迟到其子类。
https://www.zhihu.com/question/24843188
https://www.jianshu.com/p/83ef48ce635b
https://blog.csdn.net/buyulian/article/details/79203880
https://blog.csdn.net/qianhaifeng2012/article/details/52014773
https://www.cnblogs.com/aspirant/p/8980573.html
http://www.akathink.com/2016/08/01/%E5%BD%BB%E5%BA%95%E6%90%9E%E6%87%82%E5%B7%A5%E5%8E%82%E6%A8%A1%E5%BC%8F/