一不小心都看了十种设计模式了,准备好好整理下,才发现还有个抽象工厂模式是被之前搁置下来的,是时候理解真正的抽象工厂模式了。
第六章 创建型设计模式——抽象工厂模式
抽象工厂模式起源于以前对不同操作系统的图形化解决方案,如不同的操作系统中的按钮和文本框其实现不同,展现效果也不一样,对每一个操作系统而言,其本身就可以构成一个产品类,而按钮和文本框控件又是其下属的产品类。
1.定义
为创建一组相关或者是相互依赖的对象提供一个接口,而不需要指定它们的具体类。
2.使用场景
1).一个对象族有相同的约束时可以使用抽象工厂模式。
这句话听起来很抽象,所以我们需要先理解一下产品族和产品等级的概念。
产品族是指位于不同产品等级结构中,功能却相关联的产品组成的家族。如宝马的刹车、引擎和轮胎组成一个家族,奔驰的刹车、引擎和轮胎又组成一个家族,但是这两个家族却包含了不同的产品等级,刹车、引擎和轮胎。
通过一张图说明一下:
所以每一个工厂创建出来的,不是工厂方法那样的一个产品,而是一族产品。这也就是它们俩最大的区别。
3.对比
将三种工厂方法的UML类图对比一下。
1).简单工厂模式:
2).工厂方法模式:
3).抽象工厂模式:
4.简单实现
从上面的图可以看出抽象工厂也分四大类:
抽象工厂类:工厂方法模式的核心。具体工厂角色的父类或实现的接口。
具体工厂类:含有具体业务逻辑,继承抽象工厂类或实现抽象工厂接口。
抽象产品类:具体产品的父类或实现的接口。
具体产品类:工厂类所创建的对象。
根据上面的图,来通过代码展现一下。
先创建三个产品等级的抽象产品:
public interface Brake {
void brake();
}
public interface Engine {
void engine();
}
public interface Tire {
void tire();
}
抽象工厂:
public abstract class CarFactory {
public abstract Brake createBrake();
public abstract Engine createEngine();
public abstract Tire createTire();
}
然后根据三个产品等级分别创建三个产品族的具体产品:
Audi产品族:
public class AudiBrake implements Brake {
@Override
public void brake() {
System.out.println("Audi Brake");
}
}
public class AudiEngine implements Engine {
@Override
public void engine() {
System.out.println("Audi Engine");
}
}
public class AudiTire implements Tire {
@Override
public void tire() {
System.out.println("Audi Tire");
}
}
public class BenzBrake implements Brake {
@Override
public void brake() {
System.out.println("Benz Brake");
}
}
public class BenzEngine implements Engine {
@Override
public void engine() {
System.out.println("Benz Engine");
}
}
public class BenzTire implements Tire {
@Override
public void tire() {
System.out.println("Benz Tire");
}
}
BMW产品族:
public class BMWBrake implements Brake {
@Override
public void brake() {
System.out.println("BMW Brake");
}
}
public class BMWEngine implements Engine {
@Override
public void engine() {
System.out.println("BMW Engine");
}
}
public class BMWTire implements Tire {
@Override
public void tire() {
System.out.println("BMW Tire");
}
}
public class AudiFactory extends CarFactory {
@Override
public Brake createBrake() {
return new AudiBrake();
}
@Override
public Engine createEngine() {
return new AudiEngine();
}
@Override
public Tire createTire() {
return new AudiTire();
}
}
public class BenzFactory extends CarFactory {
@Override
public Brake createBrake() {
return new BenzBrake();
}
@Override
public Engine createEngine() {
return new BenzEngine();
}
@Override
public Tire createTire() {
return new BenzTire();
}
}
public class BMWFactory extends CarFactory {
@Override
public Brake createBrake() {
return new BMWBrake();
}
@Override
public Engine createEngine() {
return new BMWEngine();
}
@Override
public Tire createTire() {
return new BMWTire();
}
}
在客户端中调用:
CarFactory mAudiFactory = new AudiFactory();
mAudiFactory.createBrake().brake();
mAudiFactory.createEngine().engine();
mAudiFactory.createTire().tire();
CarFactory mBMWFactory = new BMWFactory();
mBMWFactory.createBrake().brake();
mBMWFactory.createEngine().engine();
mBMWFactory.createTire().tire();
CarFactory mBenzFactory = new BenzFactory();
mBenzFactory.createBrake().brake();
mBenzFactory.createEngine().engine();
mBenzFactory.createTire().tire();
可以看到每个工厂的产品族的产品都创建了:
5.总结
抽象工厂模式在Android开发中使用得并不多,因为实际开发中很少会出现多个产品种类的情况,大部分情况使用工厂模式即可解决。
优点:
1).分离接口和实现,客户端使用抽象工厂来创建所需对象,但却并不知道具体的实现是谁,使其从产品的实现中解耦,更灵活。
缺点:
1).类的爆炸性增加,如果要增加一个工厂,那么相应的,就得增加一族产品。
2).不容易扩展新的产品类,因为当我们增加一个产品类时就需要修改抽象工厂,所以所有的具体工厂类也得对应修改。