22 行为型模式-状态模式

1 状态模式介绍
2 状态模式结构


3 状态模式实现

代码示例

java 复制代码
//抽象状态接口
public interface State {
	//声明抽象方法,不同具体状态类可以有不同实现
	void handle(Context context);
}
java 复制代码
/**
 * 上下文类
 **/
public class Context {

    //维持一个对状态对象的有引用
    private State currentState;

    public Context() {
        this.currentState = null;
    }

    public Context(State currentState) {
        this.currentState = currentState;
    }

    public State getCurrentState() {
        return currentState;
    }

    public void setCurrentState(State currentState) {
        this.currentState = currentState;
    }

    @Override
    public String toString() {
        return "Context{" +
                "currentState=" + currentState +
                '}';
    }
}
java 复制代码
public class ConcreteStateA implements State {

    @Override
    public void handle(Context context) {
        System.out.println("进入到状态模式A......");
        context.setCurrentState(this);
    }

    @Override
    public String toString() {
        return "当前状态: ConcreteStateA";
    }
}
java 复制代码
public class ConcreteStateB implements State {

    @Override
    public void handle(Context context) {
        System.out.println("进入到状态模式B......");
        context.setCurrentState(this);
    }

    @Override
    public String toString() {
        return "当前状态: ConcreteStateB";
    }
}
java 复制代码
public class Client {

    public static void main(String[] args) {

        Context context = new Context();

        State state1 = new ConcreteStateA();
        state1.handle(context);
        System.out.println(context.getCurrentState().toString());

        System.out.println("=================================");
        State state2 = new ConcreteStateB();
        state2.handle(context);
        System.out.println(context.getCurrentState().toString());
    }
}
4 状态模式应用实例
  1. 不使用设计模式
java 复制代码
/**
 * 交通灯类有三种状态
 *     红灯(禁行) ,黄灯(警示),绿灯(同行)
 **/
public class TrafficLight {

    //初始化状态
    private String state = "红色";

    //切换为绿灯,通行状态
    public void switchToGreen(){
        if("绿".equals(state)){ //当前是绿灯
            System.out.println("当前为绿灯,无需切换!");
        }else if("红".equals(state)){
            System.out.println("红灯不能切换为绿灯");
        }else if("黄".equals(state)){
            state = "绿";
            System.out.println("绿灯亮起...时长: 60秒");
        }
    }

    //切换为黄灯,警示状态
    public void switchToYellow() {
        if ("黄".equals(state)) { //当前是黄灯
            System.out.println("当前为黄灯,无需切换!");
        } else if ("红".equals(state) || "绿".equals(state)) {
            System.out.println("红灯不能切换为绿灯");
            state = "黄";
            System.out.println("黄灯亮起...时长:10秒");
        }
    }

    //切换为红灯,禁止状态
    public void switchToRed(){
        if("红".equals(state)){ //当前是红灯
            System.out.println("当前为红灯,无需切换!");
        }else if("绿".equals(state)){
            System.out.println("绿灯不能切换为红灯");
        }else if("黄".equals(state)){
            state = "红";
            System.out.println("红灯亮起...时长: 90秒");
        }
    }
}

问题: 状态切换的操作全部在一个类中,如果有很多的交通灯进行联动,这个程序

的逻辑就会变得非常复杂,难以维护.

2) 使用状态模式,将交通灯的切换逻辑组织起来,把跟状态有关的内容从交通灯类
里抽离出来,使用类来表示不同的状态.

java 复制代码
/**
 * 交通灯类
 **/
public class TrafficLight {

    //初始化-红灯
    State state =  new RedState();

    public void setState(State state) {
        this.state = state;
    }

    //切换为绿灯,通行状态
    public void switchToGreen(){
        state.switchToGreen(this);
    }

    //切换为黄灯,警示状态
    public void switchToYellow() {
        state.switchToYellow(this);
    }

    //切换为红灯,禁止状态
    public void switchToRed(){
        state.switchToRed(this);
    }

}
java 复制代码
/**
 * 交通灯状态接口
 **/
public interface State {

    void switchToGreen(TrafficLight trafficLight);  //切换为绿灯

    void switchToYellow(TrafficLight trafficLight);  //切换为黄灯

    void switchToRed(TrafficLight trafficLight);  //切换为红灯
}
java 复制代码
public class RedState implements State {

    @Override
    public void switchToGreen(TrafficLight trafficLight) {
        System.out.println("红灯不能切换为绿灯!");
    }

    @Override
    public void switchToYellow(TrafficLight trafficLight) {
        System.out.println("黄灯亮起...时长: 10秒");
    }

    @Override
    public void switchToRed(TrafficLight trafficLight) {
        System.out.println("当前为红灯,无需切换!");
    }
}
java 复制代码
public class GreenState implements State {

    @Override
    public void switchToGreen(TrafficLight trafficLight) {
        System.out.println("当前是绿灯,无需切换!");
    }

    @Override
    public void switchToYellow(TrafficLight trafficLight) {
        System.out.println("黄灯亮起...时长: 10秒");
    }

    @Override
    public void switchToRed(TrafficLight trafficLight) {
        System.out.println("绿灯不能够切换为红灯!");
    }
}
java 复制代码
public class YellowState implements State {

    @Override
    public void switchToGreen(TrafficLight trafficLight) {
        System.out.println("绿灯亮起...时长:60秒!");
    }

    @Override
    public void switchToYellow(TrafficLight trafficLight) {
        System.out.println("当前是黄灯,无需切换!");
    }

    @Override
    public void switchToRed(TrafficLight trafficLight) {
        System.out.println("红灯亮起...时长:90秒!");
    }
}
java 复制代码
public class Client {

    public static void main(String[] args) {

        TrafficLight trafficLight = new TrafficLight();
        trafficLight.switchToRed();
        trafficLight.switchToGreen();
        trafficLight.switchToYellow();
    }
}

通过代码重构,将"状态" 接口化、模块化,最终将它们从臃肿的交通类中抽了出来,

消除了原来TrafficLight类中的if...else,代码看起来干净而优雅.

5 状态模式总结
相关推荐
m0_587383008 小时前
无人自助拼豆系统从需求分析到落地部署全流程实战开发指南
java·经验分享·后端·struts·小程序·架构·需求分析
a努力。8 小时前
四维解析Agent记忆架构:从零实战LangGraph长期记忆
java·开发语言·数据库
碧海银沙音频科技研究院8 小时前
炬芯ATS308X的扩音器:麦克风到扬声器直通功能实现
java·linux·运维
Rain的Java大神之路8 小时前
被问麻了!Function Calling、MCP、Skill 到底啥关系?一张图讲透三层架构,附 Java 生产落地全流程+30个坑
java·后端·ai编程
Wang's Blog8 小时前
Java 项目部署之 Docker工具快速入门: Docker Compose 初识与安装
java·开发语言·docker
niucloud-admin8 小时前
JAVA V6 多商户商城 开发文档——项目启动
java·开发语言·python
学逆向的8 小时前
C 控制台指令
c语言·开发语言·网络安全
沫璃染墨8 小时前
从零入门数据结构与算法(一):复杂度分析——从算法效率到时间与空间复杂度
c语言·开发语言·数据结构·笔记·算法·飞书
众链网络9 小时前
Agent 重试的工程解法:幂等、断点续跑与熔断怎么落地
java·前端·数据库·人工智能
贾宝玉的玉宝贾9 小时前
FreeSWITCH 简单图形化界面 70 - 监听/密语的lua脚本
开发语言·junit·lua·voip·freeswitch·sip·ippbx