23种设计模式——状态模式(State Pattern)

✅作者简介:大家好,我是 Meteors., 向往着更加简洁高效的代码写法与编程方式,持续分享Java技术内容。
🍎个人主页:Meteors.的博客
💞当前专栏:设计模式
✨特色专栏:知识分享
🥭本文内容:23种设计模式------状态模式(State Pattern)
📚 ** ps ** :阅读文章如果有问题或者疑惑,欢迎在评论区提问或指出。


目录

[一. 介绍](#一. 介绍)

[二. 概念](#二. 概念)

[三. 组成结构](#三. 组成结构)

[四. 代码示例](#四. 代码示例)

[五. 优缺点](#五. 优缺点)

[1. 优点](#1. 优点)

[2. 缺点](#2. 缺点)

[六. 适用场景](#六. 适用场景)

[七. 总结](#七. 总结)


一. 介绍

状态模式,如果单凭这个名字,我们可能不太清楚这个是什么。如果用一个很经典的例子来形容,就是外卖订单各种状态的管理,将它们区分成很多种状态类,每种状态类只要管理这个状态的实现和定义上下状态的切换的方法就够了。可能你现在还是不太理解,下面内容将会为你详细的介绍这种设计模式。


二. 概念

状态模式是一种行为型设计模式,它允许对象在其内部状态改变时改变它的行为,看起来就像是对象的类发生了改变一样。

状态模式的***核心是将状态与状态对应的行为封装到单独的类中,并将状态委托给当前的状态对象。***当对象的状态改变时,它会改变自己的行为,而无需修改原有类。


三. 组成结构

状态模式包含以下主要角色:

角色 名称
​Context(上下文) 定义客户感兴趣的接口,维护一个当前状态对象的引用
​State(抽象状态) 定义一个接口以封装与Context的一个特定状态相关的行为
ConcreteState(具体状态) 实现与Context的一个状态相关的行为

四. 代码示例

我们以一个实现了状态模式的简单订单状态Java代码为例:

java 复制代码
// 状态接口
interface OrderState {
    void next(Order order);
    void previous(Order order);
    void printStatus();
}

// 具体状态:已创建
class CreatedState implements OrderState {
    @Override
    public void next(Order order) {
        order.setState(new PaidState());
    }

    @Override
    public void previous(Order order) {
        System.out.println("订单已创建,没有更前的状态");
    }

    @Override
    public void printStatus() {
        System.out.println("订单已创建,等待支付");
    }
}

// 具体状态:已支付
class PaidState implements OrderState {
    @Override
    public void next(Order order) {
        order.setState(new ShippedState());
    }

    @Override
    public void previous(Order order) {
        order.setState(new CreatedState());
    }

    @Override
    public void printStatus() {
        System.out.println("订单已支付,等待发货");
    }
}

// 具体状态:已发货
class ShippedState implements OrderState {
    @Override
    public void next(Order order) {
        order.setState(new DeliveredState());
    }

    @Override
    public void previous(Order order) {
        order.setState(new PaidState());
    }

    @Override
    public void printStatus() {
        System.out.println("订单已发货,运输中");
    }
}

// 具体状态:已送达
class DeliveredState implements OrderState {
    @Override
    public void next(Order order) {
        System.out.println("订单已完成,没有下一个状态");
    }

    @Override
    public void previous(Order order) {
        order.setState(new ShippedState());
    }

    @Override
    public void printStatus() {
        System.out.println("订单已送达");
    }
}

// 上下文类
class Order {
    private OrderState state;

    public Order() {
        this.state = new CreatedState();
    }

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

    public void nextState() {
        state.next(this);
    }

    public void previousState() {
        state.previous(this);
    }

    public void printStatus() {
        state.printStatus();
    }
}

// 客户端代码
public class StatePatternDemo {
    public static void main(String[] args) {
        Order order = new Order();
        order.printStatus();
        
        order.nextState();
        order.printStatus();
        
        order.nextState();
        order.printStatus();
        
        order.nextState();
        order.printStatus();
        
        order.previousState();
        order.printStatus();
    }
}

五. 优缺点

1. 优点

  • 将状态相关的行为局部化到一个状态类中

  • 将状态转换显式化,减少条件语句

  • 状态对象可以被多个上下文共享(如果状态对象没有实例变量)

  • 符合开闭原则,易于添加新状态

2. 缺点

  • 对于简单的状态机可能会增加不必要的复杂性

  • 状态类数量可能过多,导致类膨胀

  • 状态转换逻辑分散在各个状态类中,不易看清整体转换逻辑


六. 适用场景

  • 对象的行为依赖于它的状态
  • 代码中包含大量与对象状态有关的条件语句
  • 需要在运行时根据对象的状态动态改变对象的行为
  • 状态转换复杂且需要明确定义

七. 总结

状态模式是一种强大的设计模式,特别适合管理对象的状态和行为。通过将状态封装为独立的类,可以使代码更加清晰、可维护,并且易于扩展新的状态。

相关推荐
Query*7 小时前
Java 设计模式——适配器模式:从原理到3种实战的完整指南
java·设计模式·适配器模式
星星点点洲9 小时前
PostgreSQL 15二进制文件
开发语言·设计模式·golang
yaoxin52112310 小时前
211. Java 异常 - Java 异常机制总结
java·开发语言·python
Predestination王瀞潞14 小时前
Java EE开发技术(Servlet整合JDBC银行管理系统-上)
java·servlet·java-ee·jdbc
寻星探路14 小时前
Java EE初阶启程记13---JUC(java.util.concurrent) 的常见类
java·开发语言·java-ee
怪兽201415 小时前
什么是 Redis?
java·数据库·redis·缓存·面试
Gu_yyqx15 小时前
Java 队列
java
落日漫游15 小时前
数据结构笔试核心考点
java·开发语言·算法
疯狂吧小飞牛15 小时前
Lua C API 中的注册表介绍
java·c语言·lua