定义
任何可以产生对象的类或方法,我么都可以称为工厂。
背景
为什么可以通过new的方式去创建对象,还需要通过工厂去构建呢?实际上是因为一个对象可能比较复杂,以及需要很多外部的配置参数,工厂可以帮我们屏蔽掉这些信息,让我们更专注于对象的使用,而非构建。
案列场景
当人外出旅行时,可以采用不同的交通工具去一个地方。正常可以采用如下方案:
public class Car {
public void go(){
System.out.println("汽车出发了~");
}
}
public class Plan {
public void go(){
System.out.println("飞机飞行了~");
}
}
public class Train {
public void go(){
System.out.println("火车开动了~");
}
}
public class Person {
public static void main(String[] args) {
// Car car =new Car();
// car.go();
Plan plan =new Plan();
plan.go();
}
}
该方案面临的问题就是当切换不同的工具时,需要重新创建不同的类去调用同样的方法,因为可以通过创建交通工具的父类来简化。
public interface Move {
void go();
}
public class Car implements Move {
@Override
public void go(){
System.out.println("汽车出发了~");
}
}
其他交通工具实现同样的接口,这边不在展示,person则变成如下的使用,比前面一个方案在切换工具时,简化了修改
public class Person {
public static void main(String[] args) {
Move move;
// move= new Car();
move = new Plan();
move.go();
}
}
当时当我们需要对这个工具进行使用限制的时候,就需要person里面添加限制的相关逻辑,但是又遇到了之前问题,随着工具的切换,你的限制的相关逻辑也要进行相应的变动, 但是如果采用下面的方案,则可以解决
public class SimpleVehicleFactory {
public static Car getCar(){
Car car = new Car();
System.out.println("符合驾驶资格可以使用");
return car;
}
public static Plan getPlan(){
Plan plan = new Plan();
System.out.println("已成年可以登机");
return plan;
}
}
通过类的方法去构建对应的工具实例,同时在构建的方法内添加相关的限制逻辑。这样就能屏蔽掉对象的构建过程中具体的限制逻辑。这个就是我们设计模式中的工厂模式, 属于工厂模式的简单模式的一种。它所面临的问题就是当工具不多扩展,限制不断扩展,这个类会变得巨大。不利于后续的开发。 相应的我们就可以讲方法演变成类的形式,将巨大的类拆解成多个小类。
public class CarFactory {
public static Move getCar(){
Car car = new Car();
System.out.println("符合驾驶资格可以使用");
return car;
}
}
按照这个形式将其他工具类创建对应的工厂类。这样就基本能够达到一定的扩展性。 当然,后续的我们可能会遇到不过的国家,因为不同的国家对于这些工具有不同的限制,那么我们如果继续按照上述逻辑去实现的话,会需要创建很多不同国家的同一个工具类,这样就导致了类的爆炸问题,类的数量会变多。如果我们将工厂本身进行抽象,则可以很大程度的减少类的数量问题。
public abstract class CountryVehicleFactory {
abstract Car createCar();
abstract Plan createPlan();
abstract Train createTrain();
}
public class ChineseVehicleFactory extends CountryVehicleFactory {
@Override
Car createCar() {
//中国的规则中国的车
return new Car();
}
@Override
Plan createPlan() {
//中国的飞机和规则
return new Plan();
}
@Override
Train createTrain() {
//中国的火车和规则
return new Train();
}
}
按照上述的方案,既能地扩展不同的国家的工具,同时也不会过度增加类的数量。 以上就是我们关于工厂方法和抽象工厂的讲解。