意图
工厂方法的变种。提供一个创建一系列相关或互相依赖对象的接口,而无需指定具体的类。
例子
针对动物,不同种类做具体创建。public abstract class Animal {
protected String sing;
public Animal(String sing) {
this.sing = sing;
}
// 抽象方法,用于子类使用
public abstract void show();
}
那么我就就针对下面的动物进行创建
- 陆地动物
- 海洋动物
- 飞行动物
|
根据工厂方法写出上面代码,但是并没有根据类型形成独特的工厂。public interface AbstractAnimal {
// 创建飞行动物
public Animal createFlyingAnimal();
// 创建陆地动物
public Animal createLandAnimal();
// 创建海洋动物
public Animal createMarineAnimal();
}
实现接口public class TheWorldAnimal implements AbstractAnimal{
public TheWorldAnimal() {}
// 创建飞行动物
public Animal createFlyingAnimal() {
Animal maque = new MaQue();
return maque;
}
// 创建陆地动物
public Animal createLandAnimal() {
Animal dog = new Dog();
return dog;
}
// 创建海洋动物
public Animal createMarineAnimal() {
Animal longxia = new LongXia();
return longxia;
}
}
这样就根据三个类型得到三个工厂,并将三个工厂集成到一个工厂中。public static void main(String[] arg) {
AbstractAnimal factory = new TheWorldAnimal();
Animal flyingAnimal = factory.createFlyingAnimal();
flyingAnimal.show();
Animal landAnimal = factory.createLandAnimal();
landAnimal.show();
Animal marineAnimal = factory.createMarineAnimal();
marineAnimal.show();
}
适用性
- 一个系统要独立于他的产品的创建、组合和表示时
- 一个系统要由多个产品系列中的一个来配置时
- 当你要强调一个系列相关的产品对象的设计以便进行联合使用
- 当你提供一个产品类库,而只想显示他们的接口而不是实现时
结构
协作
- 通常在运行时刻创建一个ConcreteFactory类的实例。这一具体的工厂创建具有特定实现的产品对象。为创建不同的产品对象,客户应使用不同的具体工厂。
- AbstractFactory将产品对象的创建延迟到它的ConcreteFactory子类。
效果
AbstractFactory模式有下面的一些优点和缺点:
- 它分离了具体的类,AbstractFactory模式帮助你控制一个应用创建的对象的类。因为一个工厂封装创建产品对象的责任和过程,它将客户与类的实现分离。客户通过它们的抽象接口操纵实例。产品的类名也在具体工厂的实现中被分离;它们不出现在客户代码中。
- 它使得易于交换产品系列一个具体工厂类在一个应用中仅出现一次—即在它初始化的时候。这使得改变一个应用的具体工厂变得很容易。它只需改变具体的工厂即可使用不同的产品配置,这是因为一个抽象工厂创建了一个完整的产品系列,所以整个产品系列会立刻改变。
- 它有利于产品的一致性当一个系列中的产品对象被设计成一起工作时,一个应用一次只能使用同一个系列中的对象,这一点很重要。而AbstractFactory很容易实现这一点。
- 难以支持新种类的产品难以扩展抽象工厂以生产新种类的产品。这是因为AbstractFactory接口确定了可以被创建的产品集合。支持新种类的产品就需要扩展该工厂接口,这将涉及AbstractFactory类及其所有子类的改变。我们会在实现一节讨论这个问题的一个解决办法。