工厂方法模式(Factory Method)

在真实项目中,对象的创建往往比使用更复杂

如果你发现代码中频繁出现 if-else 或根据参数去 new 不同的类,那基本已经到了该用工厂方法模式的时候了。


一、工厂方法模式解决什么问题

先看一个非常常见的写法:

python 复制代码
def create_payment(pay_type):
    if pay_type == "wechat":
        return WeChatPay()
    elif pay_type == "alipay":
        return AliPay()
    elif pay_type == "bank":
        return BankPay()
    else:
        raise ValueError("unsupported pay type")

问题很明显:

  • 新增一种支付方式,必须修改这个函数
  • 创建逻辑与业务逻辑耦合
  • 违反开闭原则

工厂方法模式的目的就是:

把"创建对象的逻辑"从使用对象的地方解耦出来。


二、什么是工厂方法模式

**工厂方法模式(Factory Method)**的定义:

定义一个创建对象的接口,让子类决定实例化哪一个类。

核心思想:

  • 使用方只依赖抽象
  • 创建细节由工厂或子类负责

三、一个最基础的 Python 工厂方法示例

1. 抽象产品

python 复制代码
from abc import ABC, abstractmethod

class Payment(ABC):
    @abstractmethod
    def pay(self, amount):
        pass

2. 具体产品

python 复制代码
class WeChatPay(Payment):
    def pay(self, amount):
        print(f"微信支付 {amount}")

class AliPay(Payment):
    def pay(self, amount):
        print(f"支付宝支付 {amount}")

3. 工厂类

python 复制代码
class PaymentFactory:
    @staticmethod
    def create(pay_type: str) -> Payment:
        if pay_type == "wechat":
            return WeChatPay()
        if pay_type == "alipay":
            return AliPay()
        raise ValueError("unsupported pay type")

使用方:

python 复制代码
payment = PaymentFactory.create("wechat")
payment.pay(100)

四、为什么这还不够"工厂方法"

上面的写法虽然集中管理了创建逻辑,但:

  • 依然需要修改工厂代码
  • 本质还是 if-else

真正的工厂方法强调:

通过继承扩展工厂,而不是修改工厂。


五、标准工厂方法模式结构

1. 抽象工厂

python 复制代码
class PaymentFactory(ABC):
    @abstractmethod
    def create(self) -> Payment:
        pass

2. 具体工厂

python 复制代码
class WeChatPayFactory(PaymentFactory):
    def create(self) -> Payment:
        return WeChatPay()

class AliPayFactory(PaymentFactory):
    def create(self) -> Payment:
        return AliPay()

使用方式:

python 复制代码
factory = WeChatPayFactory()
payment = factory.create()
payment.pay(100)

新增支付方式时:

  • 新增产品类
  • 新增工厂类
  • 无需修改原有代码

六、Python 风格的工厂方法(推荐)

Python 中,很多时候没必要写那么多类

使用字典 + 类引用

python 复制代码
class PaymentFactory:
    _mapping = {
        "wechat": WeChatPay,
        "alipay": AliPay,
    }

    @classmethod
    def create(cls, pay_type: str) -> Payment:
        try:
            return cls._mapping[pay_type]()
        except KeyError:
            raise ValueError("unsupported pay type")

优点:

  • 代码简洁
  • 易于维护
  • 更符合 Python 风格

七、工厂方法 vs 直接实例化

对比点 直接 new 工厂方法
扩展性
解耦
可测试性
代码复杂度

适用原则:

  • 对象类型固定、变化少 → 直接实例化
  • 对象类型多、变化频繁 → 工厂方法

八、工厂方法常见误区

1. 工厂类变成"上帝类"

  • 包含大量 if-else
  • 违反单一职责

解决方案:

  • 拆分工厂
  • 或引入抽象工厂

2. 为了工厂而工厂

  • 只有一个实现类
  • 没有扩展需求

👉 直接实例化即可。


九、总结

工厂方法模式的核心价值在于:

  • 解耦创建与使用
  • 遵循开闭原则
  • 为系统预留扩展空间

在 Python 中:

  • 思想比形式重要
  • 不必拘泥 UML 结构
  • 用最简单的方式解决创建问题
相关推荐
半桶水专家2 小时前
什么是 Unix Socket?
服务器·unix
%xiao Q2 小时前
GESP C++四级-216
java·开发语言·c++
西红市杰出青年2 小时前
Python异步----------信号量
开发语言·python
鳄鱼皮坡2 小时前
设计模式(二):工厂模式
设计模式
tianyuanwo2 小时前
深入浅出SWIG:从C/C++到Python的无缝桥梁
c语言·c++·python·swig
码农幻想梦2 小时前
实验五 spring入门及IOC实验
java·后端·spring
金融小白数据分析之路2 小时前
msoffcrypto-tool库 Excel 加密
python·excel
程序员敲代码吗2 小时前
使用Python进行PDF文件的处理与操作
jvm·数据库·python
前端小臻2 小时前
软件的设计模式
设计模式