本文共 1540 字,大约阅读时间需要 5 分钟。
谈起模式一词,很多情况下笔者都认为是一个偏向贬义的词汇,代表着冥顽不灵,一成不变。细数这些年开发过程中走过的弯路后,笔者觉得设计模式真是个好东西。时代发展如此之快,我们不可能设计出一个完美的系统,但是我们可以参考一些过去的经验,少走弯路,在系统的健壮性、可扩展性上多做思考,这绝对有益于我们的系统。为此,笔者抽时间重新学习了一下设计模式,此系列文章算是学习心得吧。
简单工厂模式,又称静态方法工厂模式,其实并不属于GoF的23种设计模式中,考虑到名称上的相近之处,笔者也将其列入本系列博文中。与其说是一种设计模式,倒不如说这是一种变成习惯,我们经常能见到如下的代码:
public class SimpleFactory { public static CarInf getCar(String type){ if("SportsCar".equals(type)) return new SportsCar(); else if("FamilyCar".equals(type)) return new FamilyCar(); else return null; }}
我们经常把创建对象的逻辑封装成一个静态方法,通过参数来决定实例化哪个类。可以看到,由于工厂类集中了所有实例的创建逻辑,违反了高内聚责任分配原则
,将全部创建逻辑集中到了一个工厂类中,它所能创建的类只能是事先考虑到的,如果需要添加新的类,则就需要改变工厂类了。
既然我们不能完全考虑所有需要创建的对象,那我们把创建对象的过程推迟,这便有了工厂方法模式。工厂方法模式定义了一个创建对象的接口,但由子类来决定实例化的类是哪一个
。
工厂方法模式的类图如下:
Creator
public abstract class Creator{ abstract Product factoryMethod();}
ConcreteCreator
public class ConcreteCreator extends Creator{ public Product factoryMethod(){ return new ConcreteProduct(); }}
工厂方法模式帮助我们将产品的“实现”从“使用”中解耦出来,当我们增加产品或者改变产品的实现,Creator并不会受到影响。这便是面向对象编程七大原则之一依赖倒置原则
要依赖抽象,不要依赖具体类。
工厂方法模式让类把实例化推迟到了子类,但是存在一个问题,具体产品类和具体工厂绑定在一起,有多少个具体产品,便要有多少个具体工厂。那么对于一个具体工厂,既然能创建产品A,那也能创建产品B,这就有了产品族
的概念,即同一个具体工厂创建的一系列具体产品。
抽象工厂模式的类图如下:
AbstractFactory
public interface AbstractFactory { public AbstractProductA createProductA(); public AbstractProductB createProductB();}
抽象工厂提供一个接口,用于创建相关或者依赖对象的家族,而不需要明确指定具体类。
假设有两个工厂负责生产三种产品,如果采用工厂方法模式,那么这里面一共有2*3=6中具体产品,便要设计6个具体工厂类,但是采用抽象工厂模式,一个工厂可以生产一个产品族,因此只需要两个具体工厂类,具体工厂类数量大大减少。