# 请描述简单工厂模式的工作原理。
7 min read
Table of Contents
请描述简单工厂模式的工作原理。
简单工厂模式的工作原理
【核心定义】
简单工厂模式是一种创建型设计模式,它通过一个专门的工厂类来封装对象的创建逻辑,根据传入的参数决定创建哪种具体产品类的实例,从而将客户端代码与具体产品的实现解耦。
【关键要点】
- 核心角色分离:将对象的创建职责从客户端代码中剥离,集中到工厂类中,符合单一职责原则。
- 参数化创建:工厂类通常提供一个静态方法(如
createProduct),根据传入的字符串、枚举或类型参数来实例化对应的具体产品。 - 面向接口编程:客户端代码依赖抽象的产品接口或父类,而非具体实现类,提高了系统的灵活性和可扩展性。
【深度推导/细节】
核心矛盾与解决逻辑
- 矛盾:客户端需要创建多种相关对象,如果直接
new具体类,会导致代码与具体类强耦合,且当需要新增或修改产品时,必须多处修改客户端代码。 - 解决逻辑:
- Step 1: 定义一个抽象产品接口或父类,声明产品的公共方法。
- Step 2: 创建多个具体产品类,实现该接口或继承该父类。
- Step 3: 创建工厂类,内含一个静态方法。该方法接收一个标识参数,通过
if-else或switch逻辑判断,new出对应的具体产品并返回抽象类型。 - Step 4: 客户端调用工厂方法获取产品,无需知晓具体类名。
典型代码结构
// 1. 抽象产品interface Product { void use();}
// 2. 具体产品class ConcreteProductA implements Product { @Override public void use() { System.out.println("Using Product A"); }}class ConcreteProductB implements Product { @Override public void use() { System.out.println("Using Product B"); }}
// 3. 简单工厂class SimpleFactory { public static Product createProduct(String type) { if ("A".equals(type)) { return new ConcreteProductA(); } else if ("B".equals(type)) { return new ConcreteProductB(); } throw new IllegalArgumentException("Unknown product type."); }}
// 4. 客户端public class Client { public static void main(String[] args) { Product product = SimpleFactory.createProduct("A"); product.use(); // 输出: Using Product A }}【关联/对比】
- 与工厂方法模式对比:
- 简单工厂:一个工厂类负责创建所有产品,通过条件判断决定创建对象。增加新产品需要修改工厂类的逻辑,违反了开闭原则。
- 工厂方法:定义一个创建对象的接口,但让子类决定实例化哪个类。每个具体产品对应一个具体工厂,符合开闭原则。
- 与抽象工厂模式对比:
- 简单工厂:创建单一产品等级结构(同一接口的不同实现)。
- 抽象工厂:创建多个产品族(一组相关或依赖的对象),强调产品家族的创建。
『面试官追问』
-
简单工厂模式的优缺点是什么?
- 优点:客户端与具体产品解耦;职责清晰,将创建逻辑集中管理。
- 缺点:工厂类职责过重,一旦无法工作,整个系统受影响;增加新产品必须修改工厂类代码,违反了开闭原则;由于使用静态方法,工厂类无法形成基于继承的等级结构。
-
简单工厂模式违反了开闭原则,为什么还要使用它?
- 在产品类型固定、很少变化的场景下(如JDK中的
Calendar.getInstance()、NumberFormat等),简单工厂足够简洁有效。它是一种“妥协的优雅”,在复杂性和灵活性之间取得平衡。
- 在产品类型固定、很少变化的场景下(如JDK中的
-
简单工厂模式中,工厂类的方法为什么通常设计为静态的?
- 为了方便客户端调用,无需实例化工厂对象。这强调了它作为“工具类”的角色,但同时也意味着工厂类无法通过继承来多态化,降低了灵活性。
-
能否举一个JDK或Spring中使用简单工厂模式的例子?
- JDK:
java.util.Calendar#getInstance()根据Locale和TimeZone创建不同的日历实例。 - Spring:
BeanFactory虽然本质上是工厂方法模式,但其getBean(String name)方法根据Bean名称返回对象,在单一方法内进行复杂决策,具有简单工厂的思想痕迹。
- JDK:
【设计思想与适用场景】
- 设计思想:封装变化点。将对象创建这个易变点封装起来,使客户端代码保持稳定。
- 适用场景:
- 工厂类负责创建的对象数量较少,逻辑不复杂。
- 客户端只关心产品的接口,不关心具体实现和创建细节。
- 产品类型相对固定,新增或变更频率低。
总结:简单工厂模式是工厂模式家族中最基础的一种,它通过引入一个中间层,解耦了客户端与具体产品,是学习更复杂工厂模式(工厂方法、抽象工厂)的重要基础。其核心价值在于封装创建逻辑和实现客户端与产品的解耦。