抽象工厂模式是一种创建型设计模式,它提供一个接口,用于创建与产品有关的对象簇,因而也被称为 ”工具箱“ 或 ”工具包”。抽象工厂允许客户端使用界面来创建一组相关的对象,而不需要指定它们的具体类。
工厂方法模式中考虑的是一类产品的生产,如畜牧场只养动物、电视机厂只生产电视机、传智播客只培养计算机软件专业的学生等。
有关工厂方法模式的详细介绍请查看:【创建型-2】设计模式之-工厂方法模式 - 知乎
工厂方法模式生产同种类产品,同种类产品称为同等级产品,也就是说:工厂方法模式只考虑生产同等级的产品。
但是在现实生活中许多工厂是综合型的工厂,能生产多等级(种类) 的产品,如电器厂既生产电视机又生产洗衣机或空调,大学既有软件专业又有生物专业等。
抽象工厂模式将考虑多等级产品的生产,将同一个具体工厂所生产的位于不同等级的一组产品称为一个产品族。
抽象工厂模式通常由以下几种角色组成:
-
抽象工厂 (Abstract Factory) :定义了一个接口,用于创建不同种类的产品。
-
具体工厂 (Concrete Factory) :实现抽象工厂接口,并负责实例化产品。
-
抽象产品 (Abstract Product) :定义产品的基本属性和方法。
-
具体产品 (Concrete Product) :实现抽象产品接口,即给出具体的实现。
例如:在咖啡店中往往有很多甜品可以提供,不仅仅可以生产咖啡【Coffee,如美式、拿铁等等】,还可以生产甜品【Dessert,如提拉米苏、抹茶慕斯等等】。
要是按照工厂方法的方式进行创建。需要定义提拉米苏类、抹茶慕斯类、提拉米苏工厂、抹茶慕斯工厂、甜点工厂类,很容易发生类爆炸情况。
其中拿铁咖啡、美式咖啡是一个产品等级,都是咖啡;提拉米苏、抹茶慕斯也是一个产品等级;拿铁咖啡和提拉米苏是同一产品族(也就是都属于意大利风味),美式咖啡和抹茶慕斯是同一产品族(也就是都属于美式风味)
案例代码实现:
1、创建抽象工厂接口【AbstractFactory】,里面提供生产咖啡和甜点的抽象方法
/**
* 定义抽象工厂,可以用来制作咖啡和甜点
**/
public interface AbstractFactory {
Coffee createCoffee();
Dessert createDessert();
}
2、创建抽象产品,咖啡【Coffee】和甜点【Dessert】抽象类
public abstract class Coffee {
public abstract String getName();
public void addMilk(){
System.out.println("加奶。。");
}
public void addSugar(){
System.out.println("加糖。。");
}
}
public abstract class Dessert {
public abstract void show();
}
3、创建具体产品类,具体的甜点【提拉米苏(TiLaMiSu)和抹茶慕斯(MoChaMuSi)】和具体的咖啡【拿铁(NatieCoffee)和美式(AmericaCoffee)】
public class TiLaMiSu extends Dessert{
@Override
public void show() {
System.out.println("提拉米苏");
}
}
public class MoChaMuSi extends Dessert{
@Override
public void show() {
System.out.println("抹茶慕斯");
}
}
public class NatieCoffee extends Coffee {
@Override
public String getName() {
return "拿铁咖啡";
}
}
public class MeishiCoffee extends Coffee {
@Override
public String getName() {
return "美式咖啡";
}
}
4、创建具体的工厂【美式风格工厂(AmericaFactory)和意大利风格工厂(ItalyFactory)】
/**
* 美食工厂,生产美式咖啡和美式甜点
**/
public class AmericaFactory implements AbstractFactory{
@Override
public Coffee createCoffee() {
return new MeishiCoffee();
}
@Override
public Dessert createDessert() {
return new MoChaMuSi();
}
}
public class ItalyFactory implements AbstractFactory{
@Override
public Coffee createCoffee() {
return new NatieCoffee();
}
@Override
public Dessert createDessert() {
return new TiLaMiSu();
}
}
5、测试产品
public static void main(String[] args) {
//创建一个美式工厂
AbstractFactory factory = new AmericaFactory();
//生产美式咖啡
Coffee coffee = factory.createCoffee();
coffee.addMilk();
coffee.addSugar();
String coffeeName = coffee.getName();
System.out.println("coffeeName = " + coffeeName);
//生产美式甜点【抹茶慕斯】
Dessert dessert = factory.createDessert();
dessert.show();
System.out.println("------------------------");
//创建一个意大利工厂
AbstractFactory factory1 = new ItalyFactory();
//生产拿铁咖啡
Coffee coffee1 = factory1.createCoffee();
String coffee1Name = coffee1.getName();
System.out.println("coffee1Name = " + coffee1Name);
//生产意大利甜点【提拉米苏】
Dessert dessert1 = factory1.createDessert();
dessert1.show();
}
//测试结果
加奶。。
加糖。。
coffeeName = 美式咖啡
抹茶慕斯
------------------------
coffee1Name = 拿铁咖啡
提拉米苏
抽象工厂模式通过引入抽象层来实现对象创建的依赖关系解耦、提高代码复杂度处理的灵活性和可扩展性。 在这个模式中,工厂中维护一个对象族,这族对象的特点是具有相互关联或者相互依赖的关系,在一些工程实践场景中,则代表着对系统架构层面 和业务处理流程层面上的一起考虑和设计。抽象工厂模式通常适用于以下几种场景:
-
需要创建复杂的对象族,且其中有相互依赖关系。抽象工厂可以适应这种情况,使得在创建对象族时更加灵活方便。
-
系统需要独立于它的产品的创建、组合和表示时。抽象工厂为每个产品族提供一个工厂类,客户端使用的是接口,而不是实现,从而使得系统只依赖于接口,而与具体实现无关。
-
强调一致性的设计中,适用于团队开发利于约定统一规范而减少自由度以避免造成代码风格特别多的问题。