比如我要一个手机,我可以直接把钱给厂商,他就能造一个手机给我,我不需要关心手机是如何造出来的,这是简单工厂模式。如果,我今天要一部小米,明天要一部三星,后天要一部苹果,那么我的简单工厂内部逻辑就需要一直修改,这就违背了开闭原则(对扩展开放,对修改封闭)–这就引申出我们今天的工厂方法模式。
1、定义
工厂方法模式去掉了工厂中的静态创建方法,定义为抽象方法,使得子工厂可以继承实现该方法,创建具体对象。
2. 角色
- 抽象工厂角色(1个):工厂方法模式的核心,把对象的实现方法抽象出来,让子类来实现,同时该角色还具备一些操作,子类可直接使用。
- 具体工厂角色(多个):实现抽象工厂接口或者继承抽象工厂类,实现创建对象的方法。
- 抽象产品角色(1个):它是具体的产品的父接口或者父类。
- 具体产品角色(多个):具体工厂角色创建的对象。
3. 编写各个角色代码
需求:创建小米和iPhone,并且创建工厂能直接提供说明书。
3.1 抽象工厂
定义该创建器的一些共有方法和抽象对象创建方法
/**
* 抽象工厂角色
* Created by rytong on 2017/10/10.
*/
public abstract class Factory {
private static final String TAG = Factory.class.getSimpleName();
/**
* 抽象工厂方法
*
* @return
*/
protected abstract ProductObject createProduct();
// 产品说明书
public void productInstruction(){
ProductObject product = createProduct();
Log.e(TAG,product.getInstruction());
}
}
3.2 抽象产品
抽象各产品的共有方法,实现交给子类
/**
* 抽象产品角色
* Created by rytong on 2017/10/10.
*/
public abstract class ProductObject {
public abstract String getInstruction();
}
3.3 具体产品
/**
* 具体的产品角色:小米
* Created by rytong on 2017/10/10.
*/
public class XiaoMiPhone extends ProductObject {
@Override
public String getInstruction() {
return "这是小米说明书";
}
}
3.4 具体工厂
/**
* 生产小米对象
* Created by rytong on 2017/10/10.
*/
public class XiaoMiFactory extends Factory {
@Override
protected ProductObject createProduct() {
return new XiaoMiPhone();
}
}
4. 调用端调用
调用代码
IPhoneFactory iPhoneFactory = new IPhoneFactory();
iPhoneFactory.productInstruction();
XiaoMiFactory xiaoMiFactory = new XiaoMiFactory();
xiaoMiFactory.productInstruction();
运行效果:
10-10 12:45:28.449 27756-27756/? E/Factory: 这是iPhone说明书
10-10 12:45:28.459 27756-27756/? E/Factory: 这是小米说明书
5. 总结
工厂方法模式使用多个抽象工厂的子类代替简单工厂中的逻辑判断部分代码,这样的话使得结构更加灵活,如果有增加需求,只需要再添加子工厂和子产品,而不需要动原有代码,这很符合开闭原则。
Arrylist和List中的iterator就是这个原理。