设计模式实战:状态模式(State)

在很多业务系统中,你一定遇到过这种代码:

python 复制代码
def handle(order):
    if order.status == "created":
        ...
    elif order.status == "paid":
        ...
    elif order.status == "shipped":
        ...
    elif order.status == "completed":
        ...

刚开始还好,但随着业务发展:

  • 状态越来越多
  • 状态之间有流转规则
  • 每个状态逻辑越来越复杂

代码会变成:

巨型 if/else 地狱

这正是 状态模式(State) 要解决的问题。


一、状态模式解决什么问题?

一句话:

允许对象在内部状态改变时改变它的行为,看起来像改变了对象本身。

关键词:

  • 状态驱动行为
  • 消除 if/else
  • 状态流转
  • 行为封装

二、一个典型场景:订单状态流转

订单常见状态:

text 复制代码
创建 → 已支付 → 已发货 → 已完成

不同状态下:

  • 能执行的操作不同
  • 行为逻辑不同

例如:

状态 可操作
创建 支付、取消
已支付 发货
已发货 收货
已完成

如果用 if/else:

  • 状态判断到处都是
  • 修改一个状态影响全局

三、状态模式的核心思想

把"状态"变成对象。

结构:

复制代码
Context  --->  State
                 |
        -------------------
        |        |        |
   StateA   StateB   StateC

核心:

  • 每个状态一个类
  • 状态负责行为
  • 状态可以切换

四、Python 实现状态模式

1️⃣ 定义状态接口

python 复制代码
from abc import ABC, abstractmethod

class OrderState(ABC):

    @abstractmethod
    def handle(self, order):
        pass

2️⃣ 具体状态类

python 复制代码
class CreatedState(OrderState):

    def handle(self, order):
        print("订单创建,可以支付")
        order.set_state(PaidState())


class PaidState(OrderState):

    def handle(self, order):
        print("已支付,准备发货")
        order.set_state(ShippedState())


class ShippedState(OrderState):

    def handle(self, order):
        print("已发货,等待收货")
        order.set_state(CompletedState())


class CompletedState(OrderState):

    def handle(self, order):
        print("订单已完成")

3️⃣ 上下文(Context)

python 复制代码
class Order:

    def __init__(self):
        self.state = CreatedState()

    def set_state(self, state):
        self.state = state

    def process(self):
        self.state.handle(self)

4️⃣ 使用方式

python 复制代码
order = Order()

order.process()
order.process()
order.process()
order.process()

输出:

复制代码
订单创建,可以支付
已支付,准备发货
已发货,等待收货
订单已完成

五、状态模式的核心价值

状态模式本质是:

把"状态判断逻辑"分散到各个状态类中。

它解决的是:

  • if/else 过多
  • 状态逻辑复杂
  • 状态流转难维护

六、状态模式 vs 策略模式

很多人会混淆。

它们结构很像,但核心不同:

对比点 状态模式 策略模式
目的 状态驱动行为 算法替换
是否自动切换
是否依赖上下文

一句话:

策略是"你选哪个",

状态是"系统帮你切换"。


七、更真实一点的写法(带行为约束)

在真实系统中,不同状态允许的操作不同:

python 复制代码
class CreatedState(OrderState):

    def pay(self, order):
        print("支付成功")
        order.set_state(PaidState())

    def cancel(self, order):
        print("订单取消")
python 复制代码
class PaidState(OrderState):

    def ship(self, order):
        print("发货")
        order.set_state(ShippedState())

调用:

python 复制代码
order.state.pay(order)
order.state.ship(order)

每个状态只暴露允许的操作。


八、真实项目中的应用

非常常见:

1️⃣ 订单系统

状态流转:

  • 创建 → 支付 → 发货 → 完成

2️⃣ 工作流引擎

审批流程:

  • 待审批 → 审批中 → 已通过 → 已拒绝

3️⃣ 游戏开发

角色状态:

  • 待机
  • 攻击
  • 防御
  • 死亡

4️⃣ 连接状态

TCP 状态机:

  • LISTEN
  • SYN_SENT
  • ESTABLISHED

九、状态模式优缺点

✅ 优点

  • 消除大量 if/else
  • 状态逻辑清晰
  • 易于扩展新状态
  • 符合开闭原则

❌ 缺点

  • 类数量增加
  • 结构变复杂
  • 状态过多时难管理

十、什么时候使用状态模式?

适合:

  • 状态很多
  • 状态行为不同
  • 状态有明确流转

不适合:

  • 状态很少
  • 逻辑简单

十一、一句话总结

状态模式的本质是:
把"状态"变成对象,让状态自己决定行为。

换句话说:

不要用 if/else 判断状态,让状态自己说该干什么。


相关推荐
咖啡八杯2 小时前
GoF设计模式——解释器模式
java·后端·spring·设计模式
想会飞的蒲公英4 小时前
计算机怎样读取中文文本:编码、清洗与标准化
人工智能·python·自然语言处理
SeaTunnel4 小时前
从 Python Script 地狱到标准化数据集成框架
大数据·开发语言·python·程序员·代码·seatunnel
深度研习笔记5 小时前
OpenCV工业视觉实战09|项目EXE打包+工控机无环境部署+后台常驻运行,彻底脱离Python环境,完成项目最终交付
python·opencv·webpack
CCPC不拿奖不改名5 小时前
大模型推理架构与开源生态知识整理
数据库·windows·python·架构·langchain·开源·github
大数据新鸟5 小时前
设计模式四大基本原则
设计模式
Marst Code5 小时前
(python)2026Plotly 库评估:交互式可视化到底值不值得引入?
开发语言·python
databook5 小时前
当散点图不够用时:用 t-SNE 可视化多维数据
python·数据分析·数据可视化
我的xiaodoujiao8 小时前
快速学习Python基础知识详细图文教程9--函数进阶
开发语言·python·学习·测试工具
weixin_408099678 小时前
2026 图片去水印 API 接口完全指南:一键去除图片水印(附 Python/Java/PHP/C# 示例)
java·python·php·图片处理·api调用·图片去水印·石榴智能