设计模式之状态模式

状态模式

其他模式

状态模式是一种行为设计模式, 让你能在一个对象的内部状态变化时改变其行为, 使其看上去就像改变了自身所属的类一样。

它主要用来解决对象在多种状态转换时,需要对 输出不同的行为的问题。状态和行为是一一对应的,状态之间可以相互转换

当一个对象的内在状态改变时,允许改变其行为,这个对象看起来像是改变了其类

概括:允许一个对象在其内部状态发生改变时改变其行为能力。
核心:改变一个对象的状态时,输出不同的行为。

模式结构

  • 环境类(Context)角色:也称为上下文,它定义了客户端需要的接口,内部维护一个当前状态,并负责具体状态的切换。
  • 抽象状态(State)角色:定义一个接口,用以封装环境对象中的特定状态所对应的行为,可以有一个或多个行为。
  • 具体状态(Concrete State)角色:实现抽象状态所对应的行为,并且在需要的情况下进行状态切换。

类图

在这里插入图片描述
在这里插入图片描述

优缺点

优点

  • 代码有很强的可读性。状态模式将每个状态的行为封装到对应的一个类中
  • 单一职责原则。 将与特定状态相关的代码放在单独的类中。
  • 开闭原则。 无需修改已有状态类和上下文就能引入新状态。
  • 方便维护。将容易产生问题的if-else语句删除了,如果把每个状态的行为都放到一
    个类中,每次调用方法时都要判断当前是什么状态,不但会产出很多if-else语句,而且容易出错。

缺点

  • 如果状态机只有很少的几个状态, 或者很少发生改变, 那么应用该模式可能会显得小题大作。
  • 状态模式的使用必然会增加系统的类与对象的个数,容易造成类爆炸。
  • 状态模式的结构与实现都较为复杂,如果使用不当会导致程序结构和代码的混乱。

应用场景

  • 当一个事件或者对象有很多种状态,状态之间会相互转换,对不同的状态要求有不同的行为的时候,可以考虑使用状态模式。
  • 如果某个类需要根据成员变量的当前值改变自身行为, 从而需要使用大量的条件语句时, 可使用该模式。
  • 当相似状态和基于条件的状态机转换中存在许多重复代码时, 可使用状态模式。
  • 一个操作中含有庞大的分支结构,并且这些分支决定于对象的状态时。

示例代码

使用状态模式模拟线程切换场景
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

public class BlockedState extends ThreadState {

    public BlockedState(Status stateName) {
        System.out.println("线程处于阻塞状态");
        this.stateName = stateName;
    }

    public  void  resume(ThreadContext context){

          if (stateName == Status.BLOCKED){
              System.out.println("线程就绪:");
              context.setState(new RunnableState(Status.RUNNABLE));
          }
          else System.out.println("不是阻塞状态,无法设置就绪状态");
    }
}

public class DeadState extends  ThreadState{

    public DeadState(Status stateName){
        System.out.println("线程处于结束状态");
        this.stateName = stateName;
    }
}
public class NewState extends ThreadState {


    public NewState(Status stateName){
        System.out.println("线程处于新建状态");
        this.stateName = stateName;
    }

    public  void  start(ThreadContext context){

         if (stateName == Status.NEW){
             System.out.println("线程启动:");
             context.setState(new RunnableState(Status.RUNNABLE));
         }
         else System.out.println("已经是新建状态");

    }
}
public class RunnableState extends ThreadState {

    public RunnableState(Status stateName){
        System.out.println("线程处于就绪状态");
        this.stateName = stateName;
    }
    public  void  getCpu(ThreadContext context){

        if (stateName == Status.RUNNABLE){
            System.out.println("线程开始运行:");
            context.setState(new RunningState(Status.RUNNING));
        }
        else System.out.println("已经是就绪状态");

    }
}
public class RunningState extends ThreadState {

    public RunningState(Status stateName){
        System.out.println("线程处于运行状态");
        this.stateName = stateName;
    }

    public  void  stop(ThreadContext context){

        if (stateName == Status.RUNNING){
            System.out.println("线程设置结束:");
            context.setState(new DeadState(Status.DEAD));
        }
        else System.out.println("线程不是运行状态,无法设置为结束状态");
    }

    public  void  suspend(ThreadContext context){
        if (stateName == Status.RUNNING){
            System.out.println("线程设置阻塞:");
            context.setState(new BlockedState(Status.BLOCKED));
        }
        else System.out.println("线程不是运行状态,无法设置为阻塞状态");
    }

}
public class StatePattern {

    public static void main(String[] args) {
        ThreadState state = new  NewState(Status.NEW);
        ThreadContext context = new ThreadContext();
        context.setState(state);
        context.start();

        System.out.println(context.getState());
        context.getCpu();
        context.setState(new DeadState(Status.DEAD));
        System.out.println(context.getState());
    }
}
public enum Status {


    NEW,
    RUNNABLE,
    RUNNING,
    BLOCKED,
    DEAD

}

public class ThreadContext {

    private ThreadState state;

    public Status getState() {
        return state.stateName;
    }



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

    public void  start() {
        if (state instanceof  NewState s)
            s.start(this);
        else System.out.println("不是新建状态,无法启动");
    }
    public  void  getCpu(){
         if (state instanceof  RunnableState s)
            s .getCpu(this);
         else System.out.println("不是就绪状态,无法获取cpu");
    }
    public  void  suspend(){
        if (state instanceof  RunningState s)

           s.suspend(this);

        else  System.out.println("不是运行状态,无法设置阻塞");
    }


    public  void  stop(){
        if (state instanceof  RunningState s)

            s.stop(this);
        else  System.out.println("不是运行状态,无法设置结束");
    }

    public  void  resume() {
        if (state instanceof  BlockedState s)

         s.resume(this);
        else  System.out.println("不是阻塞状态,无法设置就绪");
    }
}
public abstract  class ThreadState {

     protected   Status stateName;


}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值