【设计模式】工厂模式

工厂方法模式深度解析:对象创建的优雅之道

一、工厂方法模式核心概念

工厂方法模式(Factory Method Pattern)是一种创建型设计模式,定义了一个创建对象的接口,但让子类决定实例化哪一个类。它将对象的实例化过程推迟到子类,实现了创建者与具体产品的解耦。

核心价值:

  • 解耦创建逻辑:将对象创建代码与使用代码分离
  • 扩展性强:新增产品类型只需添加新工厂
  • 符合开闭原则:不修改已有代码即可扩展系统
  • 统一创建入口:提供一致的实例化接口

二、为什么需要工厂方法模式?

当遇到以下场景时,工厂方法模式是理想选择:

  1. 创建逻辑复杂:对象创建需要多步初始化或条件判断
  2. 系统需要扩展:预期未来会新增产品类型
  3. 依赖抽象而非实现:客户端不应依赖具体类
  4. 资源统一管理:如数据库连接、线程池等资源的创建
graph LR Client --> Creator[创建者接口] Creator --> ConcreteCreatorA[具体创建者A] Creator --> ConcreteCreatorB[具体创建者B] ConcreteCreatorA --> ProductA[具体产品A] ConcreteCreatorB --> ProductB[具体产品B]

三、工厂方法模式实现方式大全

1. 基础实现(标准模式)

// 产品接口
interface Transport {
    void deliver();
}

// 具体产品
class Truck implements Transport {
    @Override
    public void deliver() {
        System.out.println("陆路运输:卡车送货");
    }
}

class Ship implements Transport {
    @Override
    public void deliver() {
        System.out.println("海运:货轮送货");
    }
}

// 创建者接口
interface Logistics {
    Transport createTransport();
}

// 具体创建者
class RoadLogistics implements Logistics {
    @Override
    public Transport createTransport() {
        return new Truck();
    }
}

class SeaLogistics implements Logistics {
    @Override
    public Transport createTransport() {
        return new Ship();
    }
}

// 客户端使用
public class Client {
    public static void main(String[] args) {
        Logistics logistics = new RoadLogistics();
        Transport transport = logistics.createTransport();
        transport.deliver(); // 输出:陆路运输:卡车送货
    }
}

2. 参数化工厂方法

enum TransportType { TRUCK, SHIP, AIRPLANE }

abstract class Logistics {
    // 参数化工厂方法
    public Transport createTransport(TransportType type) {
        switch (type) {
            case TRUCK: return new Truck();
            case SHIP: return new Ship();
            case AIRPLANE: return new Airplane();
            default: throw new IllegalArgumentException("未知运输类型");
        }
    }
    
    // 业务方法
    public void planDelivery() {
        Transport t = createTransport(getTransportType());
        t.deliver();
    }
    
    // 抽象方法由子类实现
    protected abstract TransportType getTransportType();
}

// 具体创建者
class FastLogistics extends Logistics {
    @Override
    protected TransportType getTransportType() {
        return TransportType.AIRPLANE;
    }
}

3. 使用Lambda表达式(Java 8+)

interface TransportFactory {
    Transport create();
}

public class LambdaFactory {
    public static void main(String[] args) {
        // 使用Lambda实现工厂
        TransportFactory truckFactory = Truck::new;
        TransportFactory shipFactory = Ship::new;
        
        Transport t1 = truckFactory.create();
        Transport t2 = shipFactory.create();
        
        t1.deliver(); // 输出:陆路运输:卡车送货
        t2.deliver(); // 输出:海运:货轮送货
    }
}

4. 带初始化参数的工厂

interface TransportFactory {
    Transport create(String model, double capacity);
}

class TruckFactory implements TransportFactory {
    @Override
    public Transport create(String model, double capacity) {
        Truck truck = new Truck();
        truck.setModel(model);
        truck.setCapacity(capacity);
        return truck;
    }
}

// 客户端使用
Transport heavyTruck = new TruckFactory()
    .create("Heavy-Duty", 20.0);

四、工厂方法模式原理深度剖析

🔍 核心机制:延迟实例化与多态绑定

工厂方法模式通过两个关键特性实现解耦:

  1. 延迟实例化:创建者类不直接实例化产品,而是通过工厂方法
  2. 多态绑定:运行时根据具体创建者类型决定产品类型
public abstract class Creator {
    // 工厂方法(核心)
    public abstract Product factoryMethod();
    
    public void businessLogic() {
        // 使用工厂方法创建产品
        Product product = factoryMethod();
        product.operation();
    }
}

✨ 设计优势解析

特性 传统创建方式 工厂方法模式
耦合度 客户端直接依赖具体类 客户端仅依赖抽象接口
扩展性 修改客户端代码才能添加新产品 只需新增具体创建者
可测试性 难模拟具体产品 易注入模拟产品
代码复用 创建逻辑重复 创建逻辑封装在工厂中

五、工厂方法模式防护措施

1. 防止无效产品创建

public abstract class Logistics {
    public Transport createTransport() {
        Transport t = createTransportInternal();
        if (!t.validate()) {
            throw new IllegalStateException("无效的运输工具");
        }
        return t;
    }
    
    protected abstract Transport createTransportInternal();
}

2. 工厂方法安全扩展

public final class SecureLogisticsFactory {
    // 防止子类覆盖核心逻辑
    public final Transport createSecureTransport() {
        Transport t = createTransport();
        enableSecurityFeatures(t);
        return t;
    }
    
    // 工厂方法可被覆盖
    protected Transport createTransport() {
        return new StandardTruck();
    }
    
    private void enableSecurityFeatures(Transport t) {
        // 添加安全特性
    }
}

六、模式对比与最佳实践

工厂方法 vs 简单工厂

特性 简单工厂 工厂方法
创建逻辑位置 集中在一个工厂类 分散在子类中
开闭原则 违反(修改工厂添加新产品) 符合(新增子类即可)
复杂度 简单 中等
适用场景 产品类型固定的小型系统 需要扩展的中大型系统

工厂方法 vs 抽象工厂

特性 工厂方法 抽象工厂
创建目标 单一产品 产品族
方法数量 一个工厂方法 多个工厂方法
层次结构 类级别 系统级别
典型场景 创建单一对象 创建相关对象集合

最佳实践建议

  1. 优先选择工厂方法:当系统预期需要扩展新产品时
  2. 结合使用模式:工厂方法常作为抽象工厂的组成部分
  3. 使用Lambda简化:Java 8+项目可用Lambda表达式简化工厂实现
  4. 避免过度设计:简单场景直接使用new更合适

七、典型应用场景

  1. 跨平台UI开发
// 创建者接口
interface GUIFactory {
    Button createButton();
    Menu createMenu();
}

// Windows实现
class WinFactory implements GUIFactory {
    public Button createButton() { return new WinButton(); }
    public Menu createMenu() { return new WinMenu(); }
}

// Mac实现
class MacFactory implements GUIFactory {
    public Button createButton() { return new MacButton(); }
    public Menu createMenu() { return new MacMenu(); }
}
  1. 数据库连接管理
interface ConnectionFactory {
    Connection createConnection();
}

class MySQLConnectionFactory implements ConnectionFactory {
    public Connection createConnection() {
        return DriverManager.getConnection(MySQL_URL);
    }
}

class OracleConnectionFactory implements ConnectionFactory {
    public Connection createConnection() {
        return DriverManager.getConnection(Oracle_URL);
    }
}
  1. 支付网关集成
interface PaymentProcessorFactory {
    PaymentProcessor createProcessor();
}

class PayPalFactory implements PaymentProcessorFactory {
    public PaymentProcessor createProcessor() {
        return new PayPalAdapter();
    }
}

class StripeFactory implements PaymentProcessorFactory {
    public PaymentProcessor createProcessor() {
        return new StripeAdapter();
    }
}

八、总结

工厂方法模式通过将对象创建过程抽象化,提供了高度灵活的系统架构:

  1. 核心优势

    • 创建逻辑与业务逻辑分离
    • 符合开闭原则,易于扩展
    • 增强代码可读性和可维护性
  2. 实现要点

    • 工厂方法使用继承实现多态创建
    • 具体创建者决定实例化哪个具体产品
    • 客户端仅依赖抽象接口
  3. 应用警示

    • 避免创建不必要的工厂层次
    • 简单场景直接实例化更高效
    • 注意工厂方法的线程安全性
graph TD A[需要创建对象?] --> B{创建逻辑是否复杂?} B -->|简单| C[直接使用 new 运算符] B -->|复杂| D{系统是否需要扩展?} D -->|是| E[使用工厂方法模式] D -->|否| F[使用简单工厂] E --> G[定义创建者接口和产品接口] G --> H[实现具体创建者和产品]

工厂方法模式是应对对象创建复杂性和系统扩展需求的利器。当系统需要灵活支持新产品类型时,该模式能显著降低代码耦合度,提高架构的可维护性。正确应用工厂方法模式,可以使你的代码在面对变化时更加从容稳定。

posted @ 2025-06-26 15:48  佛祖让我来巡山  阅读(82)  评论(0)    收藏  举报

佛祖让我来巡山博客站 - 创建于 2018-08-15

开发工程师个人站,内容主要是网站开发方面的技术文章,大部分来自学习或工作,部分来源于网络,希望对大家有所帮助。

Bootstrap中文网