在工厂方法模式当中,我们坐拥奔驰、波音、SpaceX三大工厂,分别生产奔驰汽车、波音飞机、猎鹰火箭三大顶级产品。但是这三种东西都太贵了,普通人都买不起,现在,三大公司的联合CEO为了推出新的业务(割韭菜),决定推出模型手办业务来拓展公司的商业版图。你作为三大公司的联合CEO帐下的首席软件开发工程师的助理下的实习生,要怎么实现该业务呢?
1-新增一个抽象产品类Model和三个具体产品类CarModel、PlaneModel、RocketModel
public abstract class Model {
//抽象产品——模型
public abstract String getModel();
}
public class CarModel extends Model {
private String name;
public CarModel(String name) {
this.name = name;
}
@Override
public String getModel() {
return name;
}
}
public class PlaneModel extends Model {
private String name;
public PlaneModel(String name) {
this.name = name;
}
@Override
public String getModel() {
return name;
}
}
public class RocketModel extends Model {
private String name;
public RocketModel(String name) {
this.name = name;
}
@Override
public String getModel() {
return name;
}
}
2-在抽象工厂中新增一个抽象方法buildModle(),并且在BenzFactory、BoeingFactory和SpaceFactory中实现该方法。如下代码:
public abstract class Factory {
/**
* 建造交通工具的抽象方法
* @return
*/
public abstract Vehicle buildVehicle();
/**
* 建造模型手办的抽象方法
* @return
*/
public abstract Model buildModel();
}
public class BenzFactory extends Factory {
@Override
public Vehicle buildVehicle() {
return new Car("奔驰");
}
@Override
public Model buildModel() {
return new CarModel("奔驰模型");
}
}
public class BoeingFactory extends Factory {
@Override
public Vehicle buildVehicle() {
return new Plane("波音");
}
@Override
public Model buildModel() {
return new PlaneModel("波音飞机模型");
}
}
public class SpaceXFactory extends Factory {
@Override
public Vehicle buildVehicle() {
return new Ship("宇宙飞船");
}
@Override
public Model buildModel() {
return new RocketModel("火箭模型");
}
}
3-直接调用factory.buildModel就可以了,其他的不用动
@SneakyThrows
public static void main(String[] args) {
while (true){
Scanner scanner = new Scanner(System.in);
String code = scanner.nextLine();
//新增一个map用来映射调用代号和创建路径
Map<String, String> map = new HashMap<>();
map.put("car","com.BenzFactory");
map.put("plane","com.BoeingFactory");
map.put("ship","com.SpaceXFactory");
Factory factory = (Factory) Class.forName(map.get(code)).newInstance();
Vehicle vehicle = factory.buildVehicle();
System.out.println("vehicle="+vehicle.getName());
//新增建造模型的方法
Model model = factory.buildModel();
System.out.println("model="+model.getModel());
}
}

编辑
总结一下:抽象工厂方法的本质是工厂方法的拓展,我们在工厂方法原有的基础改就行了。客户端调用的时候直接调用新的工厂方法创建新的产品就好了。使用抽象工厂方法之后,以后如果有新的公司要建造交通工具和模型手办就非常方便,只需要实现Vehicle、Model、Factory就可以了,不用修改以前的代码。但是抽象工厂方法也有缺点,在我们编写代码的过程中,我们在Factory新增的buildModel方法,改动了以前的类,这样就不符合开闭原则了(不要动以前的人的代码)。所以使用抽象工厂方法模式添加已有的产品(如交通工具、模型)就非常方便,如果添加一个Factory里没有的方法,就需要改动Factory。