这个题目非常赞!😎 很多同学写 Java 程序时,业务逻辑一复杂,if-else 嵌套就会像“意大利面”一样,难以维护。这时候 状态机(State Machine) 就能登场,用清晰的状态转移表,把复杂逻辑优雅地组织起来。

我帮你写一个详细的讲解思路,分成原理 + 三种常见实现方式 + 示例。


Java 状态机详解 —— 三种状态机实现方式优雅消灭 if-else 嵌套

1. 什么是状态机?

状态机(State Machine)是一种编程思想,用来处理状态切换事件驱动的问题。
核心要点:

  • 有限状态:系统只能处于有限的几种状态(例如:待支付已支付已发货)。
  • 事件触发:外部事件触发状态转移(如:用户付款 -> 状态从“待支付”到“已支付”)。
  • 转移规则:定义清晰的状态转移关系,避免大量 if-else 嵌套。

举个例子:订单系统状态机

待支付 --(支付成功)--> 已支付 --(发货)--> 已发货


2. 传统 if-else 的痛点

if (status.equals("待支付")) {
    if (event.equals("支付成功")) {
        status = "已支付";
    } else {
        throw new IllegalStateException("非法操作");
    }
} else if (status.equals("已支付")) {
    if (event.equals("发货")) {
        status = "已发货";
    }
} else {
    ...
}

👉 随着状态增多,代码臃肿,扩展性差。


3. 三种状态机的优雅实现方式

方式一:枚举 + 映射表(简单直观)

通过 Map<状态, Map<事件, 新状态>> 记录状态转移表。

import java.util.*;

enum State { WAIT_PAY, PAID, SHIPPED }
enum Event { PAY, SHIP }

public class EnumStateMachine {
    private static final Map&lt;State, Map&lt;Event, State>> transitions = new HashMap&lt;>();

    static {
        transitions.put(State.WAIT_PAY, Map.of(Event.PAY, State.PAID));
        transitions.put(State.PAID, Map.of(Event.SHIP, State.SHIPPED));
    }

    private State currentState = State.WAIT_PAY;

    public void fire(Event event) {
        Map&lt;Event, State> map = transitions.get(currentState);
        if (map != null &amp;&amp; map.containsKey(event)) {
            currentState = map.get(event);
            System.out.println("转移成功 -> 当前状态: " + currentState);
        } else {
            throw new IllegalStateException("非法事件: " + event + " 在状态: " + currentState);
        }
    }

    public static void main(String[] args) {
        EnumStateMachine sm = new EnumStateMachine();
        sm.fire(Event.PAY);
        sm.fire(Event.SHIP);
    }
}

✅ 优点:简洁明了,适合中小型业务。


方式二:状态模式(面向对象,扩展性强)

通过 State 接口 + 具体状态类,把状态转移逻辑封装到对象里。

interface State {
    void handle(Event event, Context ctx);
}

class WaitPay implements State {
    public void handle(Event event, Context ctx) {
        if (event == Event.PAY) {
            ctx.setState(new Paid());
            System.out.println("支付成功 -> 已支付");
        } else {
            throw new IllegalStateException("非法事件");
        }
    }
}

class Paid implements State {
    public void handle(Event event, Context ctx) {
        if (event == Event.SHIP) {
            ctx.setState(new Shipped());
            System.out.println("已发货");
        }
    }
}

class Shipped implements State {
    public void handle(Event event, Context ctx) {
        System.out.println("订单已完成");
    }
}

class Context {
    private State state = new WaitPay();
    public void setState(State state) { this.state = state; }
    public void fire(Event event) { state.handle(event, this); }
}

✅ 优点:高扩展性,符合 OOP 思想;
❌ 缺点:类数量多,结构偏重。


方式三:借助第三方库(高效 + 工程化)

例如 Spring Statemachine 或 Squirrel

Spring Statemachine 配置示例:

@Configuration
@EnableStateMachine
public class StateMachineConfig extends StateMachineConfigurerAdapter&lt;String, String> {
    @Override
    public void configure(StateMachineStateConfigurer&lt;String, String> states) throws Exception {
        states.withStates()
                .initial("WAIT_PAY")
                .state("PAID")
                .state("SHIPPED");
    }

    @Override
    public void configure(StateMachineTransitionConfigurer&lt;String, String> transitions) throws Exception {
        transitions
                .withExternal().source("WAIT_PAY").target("PAID").event("PAY")
                .and()
                .withExternal().source("PAID").target("SHIPPED").event("SHIP");
    }
}

✅ 优点:适合大型复杂系统,支持持久化、并发、安全控制;
❌ 缺点:学习成本高,配置略繁琐。


4. 总结

  • 枚举 + Map:简单实用,适合中小型项目;
  • 状态模式:面向对象,逻辑清晰,扩展性好;
  • 框架方案:工业级解决方案,适合复杂业务流程;

通过状态机,Java 开发可以彻底摆脱 if-else 的泥潭,让业务逻辑更加清晰、优雅、可维护。