深入解析工厂模式:简单工厂、工厂方法与抽象工厂的区别与应用

一、概述

深入解析工厂模式:简单工厂、工厂方法与抽象工厂的区别与应用

工厂模式是一个笼统的概念。具体划分的话有三类,分别是简单工厂模式、工厂方法模式和抽象工厂模式。简单工厂模式不属于 23 种设计模式之一,然而它们都属于创建型模式。

二、简单工厂模式

简单工厂模式,也被称作静态工厂模式(Static Factory Method)。之前已经提及,简单工厂模式并不属于 23 种设计模式之列。然而,它属于创建型模式,是工厂模式家族中最为简单且实用的模式,可将其理解为不同工厂模式的一种特殊实现。其 UML 类图如下:

从 UML 图能够得知,首先要有一个接口存在,接着是具体的产品去把这个接口予以实现,之后有一个 Factory 工厂类去生产这些产品。因为该模式并非本文的重点内容,所以仅仅在此处放置一段核心的工厂类代码即可。

public class Factory {
获取汽车的方法是根据传入的汽车类型参数来确定具体的汽车对象。如果传入的汽车类型是轿车类型,就返回一辆轿车对象;如果传入的汽车类型是卡车类型,就返回一辆卡车对象;如果传入的汽车类型是 SUV 类型,就返回一辆 SUV 对象。
            switch (carType)
            {
                case CarType.SportCarType:
                    return new SportCar();
                case CarType.JeepCarType:
                    return new JeepCar();
如果是 HatchbackCarType 这种车型的情况。
                    return new HatchbackCar();
                default:
引发一个新的异常,该异常的内容为“爱上一匹野马,可我的家里没有草原。你走吧!”;
            }
    }
}

三、工厂方法模式

工厂方法模式,也被称作多态性工厂模式,它属于设计模式三大分类里的创建型模式。它是抽象工厂模式的孪生兄弟,该模式定义了一个创建对象的接口,然而具体要实例化的类是由子类来决定的,这意味着工厂模式能将实例化工作推迟到子类去进行。

在工厂模式里,核心的工厂类不再承担所有产品的创建工作,而是把具体的创建任务交给子类去完成。这个核心类变成了一个抽象工厂的角色,它仅仅负责给出具体工厂子类必须要实现的接口,却不会去接触到底是哪一个产品应该被实例化这样的细节。

工厂方法模式很符合“开闭原则”。当要增加一个新产品时,只需增加一个具体的产品类以及与之对应的具体工厂。这样就无需关心产品的创建过程,甚至都不需要知晓具体的产品类名称。

他很好地符合了“开闭原则”。然而,每当新增一个新产品时,就需要增加两个类。这样一来,必然会导致系统的复杂度增加。其 UML 结构图如下:

示例:

产品类相关:

//抽象产品类 车
public interface Car {
    /**
     * 上班函数
     */
    void gotowork();
}
//具体产品类 自行车
公共类 Bike 实现了 Car 接口。
    @Override
    public void gotowork() {
输出“以骑自行车的方式去上班。”。
    }
}
//具体产品类  公交车
公共类 Bus 实现了 Car 接口。
    @Override
    public void gotowork() {
System 显示“坐公交车去上班!”;
    }
}

工厂类相关:

//抽象工厂
销毁汽车的方法。
    /**
     * 获取交通工具
     * 
     * @return
     */
    Car getCar();
}
//具体工厂类 生产自行车
公共类 BikeFactory 实现了 ICarFactory 接口。
    @Override
    public Car getCar() {
        return new Bike();
    }
}
//具体工厂类 生产公交车
公共类 BusFactory 实现了 ICarFactory 接口。
    @Override
    public Car getCar() {
        return new Bus();
    }
}

使用测试:

公共静态的 void 主函数(字符串数组参数 args){
    ICarFactory factory = null;
    // bike
    factory = new BikeFactory();
    Car bike = factory.getCar();
    bike.gotowork();
    // bus
    factory = new BusFactory();
    Car bus = factory.getCar();
    bus.gotowork();       
}

输出结果:

骑自行车去上班!

坐公交车去上班!

使用场景:日志记录器;数据库访问等。

四、抽象工厂模式

抽象工厂模式属于创建型设计模式。它提供一个接口,可用于创建相关或依赖对象的家族,且无需明确指定具体类。它允许客户端通过抽象接口创建一组相关产品,无需关心实际产出的具体产品是什么。这样能使客户从具体产品中解耦。

他的优点在于将具体类的生成进行了隔离,这样客户端就无需知晓究竟创建了什么。而其缺点是新增行为会较为麻烦,原因是在添加一个新产品对象时,需要对接口及其下面的所有子类进行更改。其 UML 结构图呈现如下:

具体示例:

形状接口/类

//形状接口
public interface Shape {
  void draw();
}
//具体实现类 矩形
类 Rectangle 实现了 Shape 接口。
  @Override
  public void draw() {
在 Rectangle 的 draw() 方法内部,System 进行了输出操作,输出的内容是 "Inside Rectangle::draw() method." 。
  }
}
//具体实现类正方形
公共类 Square 实现了 Shape 接口。
  @Override
  public void draw() {
System 把 "Inside Square::draw() method." 进行了输出。
  }
}
//具体实现类 圆形
类 Circle 实现了 Shape 接口。
  @Override
  public void draw() {
System 在进行输出,内容为 "Inside Circle::draw() method." 。
  }
}

颜色接口/类:

//颜色接口
public interface Color {
  void fill();
}
//具体实现类 红色
类 `Red` 实现了 `Color` 接口。
  @Override
  public void fill() {
System 进行了输出,内容为 "Inside Red::fill() method." 。
  }
}
//具体实现类 绿色
公共类 Green 实现了 Color 接口。
  @Override
  public void fill() {
System 显示了 "Inside Green::fill() method." 。
  }
}
//具体实现类 蓝色
类`Blue`实现了`Color`接口。
  @Override
  public void fill() {
System 打印出了 "Inside Blue::fill() method." 。
  }
}

工厂类:

//抽象工厂类
抽象工厂类是一个抽象类。它主要用于定义创建一系列相关或相互依赖对象的接口。这些对象通常属于一个特定的产品系列。通过使用抽象工厂类,可以在不指定具体实现类的情况下创建这些对象的实例。这样可以提高代码的可扩展性和可维护性。在实际应用中,具体的工厂类会实现抽象工厂类中定义的接口,并根据需要创建具体的产品对象。
获取指定颜色的抽象方法,参数为一个字符串类型的颜色,返回值为颜色对象。  这个方法是抽象的,需要在具体的子类中实现。  它用于获取与给定颜色字符串相对应的颜色对象。
公共抽象的 Shape 取得(字符串形状);
}
//形状工厂
公共类 ShapeFactory 继承自 AbstractFactory 类。
  @Override
如果 shapeType 为 "CIRCLE",则返回 new Circle();如果 shapeType 为 "RECTANGLE",则返回 new Rectangle();如果 shapeType 为 "TRIANGLE",则返回 new Triangle()。
    if(shapeType == null){
      return null;
    }
如果形状类型等于忽略大小写的“CIRCLE”,那么就执行以下操作;如果形状类型不等于忽略大小写的“CIRCLE”,那么就不执行以下操作。
      return new Circle();
如果 shapeType 不区分大小写地等于 "RECTANGLE",那么就执行以下操作;如果 shapeType 不区分大小写地等于 "RECTANGLE",则进行如下处理;若 shapeType 不区分大小写地等于 "RECTANGLE",就会有以下情况;要是 shapeType 不区分大小写地等于 "RECTANGLE",便会执行相应操作;当 shapeType 不区分大小写地等于 "RECTANGLE" 时,就会展开以下步骤;倘若 shapeType 不区分大小写地等于 "RECTANGLE",就会进入相应的处理流程;只要 shapeType 不区分大小写地等于 "RECTANGLE",就会触发相关操作;如果 shapeType 不区分大小写地是 "RECTANGLE",就会执行对应的操作;只要 shapeType 不区分大小写地为 "RECTANGLE",就会进行相关处理;若 shapeType 不区分大小写地属于 "RECTANGLE",就会执行特定操作;当 shapeType 不区分大小写地等同于 "RECTANGLE" 时,就会展开特定步骤;要是 shapeType 不区分大小写地和 "RECTANGLE" 相等,就会执行相应的处理;倘若 shapeType 不区分大小写地与 "RECTANGLE" 一致,就会进行相关操作。
      return new Rectangle();
如果 shapeType 不区分大小写等于 "SQUARE",那么
      return new Square();
    }
    return null;
  }
  @Override
如果传入的字符串 color 为"red",则返回红色;如果传入的字符串 color 为"green",则返回绿色;如果传入的字符串 color 为"blue",则返回蓝色;如果传入的字符串 color 为其他值,则返回 null。
    return null;
  }
}
//颜色工厂
公共类 ColorFactory 继承自 AbstractFactory 类。
  @Override
  public Shape getShape(String shapeType){
    return null;
  }
  @Override
  public Color getColor(String color) {
    if(color == null){
      return null;
    }
如果颜色等于不区分大小写的“RED”,那么就执行以下操作;如果颜色等于不区分大小写的“RED”,则执行相应的处理;若颜色等于不区分大小写的“RED”,就进行相关的操作;当颜色等于不区分大小写的“RED”时,执行对应的步骤;要是颜色等于不区分大小写的“RED”,就开展相关的工作;假如颜色等于不区分大小写的“RED”,就进行相应的处理流程;只要颜色等于不区分大小写的“RED”,就执行与之对应的动作;倘若颜色等于不区分大小写的“RED”,就开展对应的行动;若颜色等于不区分大小写的“RED”,就执行那相关的操作;当颜色等于不区分大小写的“RED”时,就进行相应的处理事宜;要是颜色等于不区分大小写的“RED”,就开展那相关的工作事宜;假如颜色等于不区分大小写的“RED”,就进行与之对应的处理流程事宜;只要颜色等于不区分大小写的“RED”,就执行那对应的动作事宜。
      return new Red();
如果 color 不区分大小写等于“GREEN”,那么
      return new Green();
如果 color 不区分大小写等于 "BLUE",那么
      return new Blue();
    }
    return null;
}

工厂生产器:

通过这个类可以方便地获取所需的工厂对象。
公共静态的抽象工厂获取工厂(字符串选择)。如果选择等于“SHAPE”,则返回 ShapeFactory 的新实例。如果选择等于“COLOR”,则返回 ColorFactory 的新实例。如果选择既不等于“SHAPE”也不等于“COLOR”,则返回 null。
如果 choice 不区分大小写等于 "SHAPE",那么
      return new ShapeFactory();
如果 choice 不区分大小写等于 "COLOR",那么就执行以下操作。
      return new ColorFactory();
    }
    return null;
  }
}

测试类:

公共类 AbstractFactoryPatternDemo 。
public static void main 函数名,其中参数为 String 类型的数组 args 。
    //获取形状工厂
AbstractFactory 是一个 shapeFactory,它是由 FactoryProducer 获取到的工厂,并且这个工厂的类型是 "SHAPE"。
    //获取形状为 Circle 的对象
Shape 被获取的形状为“CIRCLE”,通过 shapeFactory 获取到的形状是 Shape shape1 。
    //调用 Circle 的 draw 方法
    shape1.draw();
    //获取形状为 Rectangle 的对象
    //调用 Rectangle 的 draw 方法
    shape2.draw();
    //获取形状为 Square 的对象
    //调用 Square 的 draw 方法
    shape3.draw();
    
    //获取颜色工厂
抽象工厂 colorFactory 是由 FactoryProducer 获取到的工厂,其类型为"COLOR"。
    //获取颜色为 Red 的对象
    //调用 Red 的 fill 方法
    color1.fill();
    //获取颜色为 Green 的对象
    //调用 Green 的 fill 方法
    color2.fill();
    //获取颜色为 Blue 的对象
Color color3 是由 colorFactory 获取到的颜色,其颜色名称为“BLUE”。
    //调用 Blue 的 fill 方法
    color3.fill();
  }
}

输出结果:

Inside Circle::draw() method.

在 Rectangle 的 draw() 方法内部。

Inside Square::draw() method.

Inside Red::fill() method.

Inside Green::fill() method.

Inside Blue::fill() method.

使用场景:QQ换肤,一套一起换;生成不同操作系统的程序。

你可能想看:
« 上一篇
下一篇 »

相关推荐

java中什么是冒泡,冒泡算法

2026年09月06日

27阅读

java中冒号,java双冒号

2026年09月06日

26阅读

java中的->,java中的是什么意思

2026年09月06日

24阅读

java中的super用法,Java中super的说明

2026年09月06日

28阅读

java中反射的应用,java中反射的应用场景

2026年09月06日

25阅读

java中开关的定义,Java关键字有哪些

2026年09月06日

25阅读