Java设计模式(20)之状态模式

状态模式

允许对象在内部状态改变时,改变它的行为,对象看起来好像修改了它的类。当一个对象的行为改变根据它的状态而改变时,就可以使用状态模式。

类型:

行为型模式(类的状态的行为型模式)

状态模式的几个角色:

具体对象Context:维护具体状态的实例,定义当前的状态
抽象状态对象State:抽象状态接口,定义状态改变时Context对象行为改变的方法
具体状态对象ConcreteState:具体的状态对象,每一种状态对应Context对象的一种具体的行为。

状态模式的关系图:

这里写图片描述

状态模式示例:

具体对象Context:

/**
 * Create by zhaihongwei on 2018/4/2
 * Context对象
 */
public class LightContext {

    public State state;

    public LightContext() {
        // 灯的默认状态为关闭状态
        this.state = new LightOffState();
    }

    /**
     * 灯的开关,外界没有办法改变灯的打开或者关闭
     * 由灯的状态自己改变
     */
    public void onoffSwitch() {
        state.operationByState(this);
    }
}

抽象状态对象State:

/**
 * Create by zhaihongwei on 2018/4/2
 * 抽象的状态对象
 */
public interface State {

    void operationByState(LightContext light);
}

具体状态对象ConcreteState:(灯的开启状态,灯的关闭状态)

/**
 * Create by zhaihongwei on 2018/4/2
 * 灯的开启状态
 */
public class LightOnState implements State {

    @Override
    /**
     * 灯在打开的情况下,再次按下开关,灯将关闭
     */
    public void operationByState(LightContext light) {
        System.out.println("灯关闭了!");
        // 灯打开(一次点击开关按钮)之后,将灯的开关状态修改为关闭状态
        light.state = new LightOffState();
    }
}
/**
 * Create by zhaihongwei on 2018/4/2
 * 灯的关闭状态
 */
public class LightOffState implements State{

    @Override
    /**
     * 灯在关闭的情况下,再次按下开关,灯将打开
     */
    public void operationByState(LightContext light) {
        System.out.println("灯打开了!");
        // 灯关闭(一次点击开关按钮)之后,将灯的开关状态修改为开启状态
        light.state = new LightOnState();
    }
}

测试类:

/**
 * Create by zhaihongwei on 2018/4/2
 */
public class StateTest {

    public static void main(String[] args) {
        // 创建灯对象
        LightContext lightContext = new LightContext();
        // 按一次开关
        lightContext.onoffSwitch();
        // 再按一次开关
        lightContext.onoffSwitch();
    }
}

测试结果:

灯打开了!
灯关闭了!

总结:

通过上面的例子,可以看到通过状态模式将灯的状态进行了封装,将开灯和关灯的操作委托给了灯的开状态和关状态,随着状态的改变灯的行为也发生了改变。

思考:

如果之前你有学习过策略模式,就会发现状态模式的关系图和策略模式的关系图基本上是一样的,没有看到策略模式的可以看这篇文章:策略模式

扫描二维码关注公众号,回复: 2233193 查看本文章

虽然说关系图是一样的,但是两种模式的具体关注点是不同的:

  • 对于状态模式:将Context的行为改变封装到了状态对象中,Context的行为随着状态的改变而改变,而外部不需要知道内部状态的具体实现规则,只知道Context的行为改变了(如按了开关之后,知道灯开了,但并不知道灯的状态也改变了)
  • 对于策略模式:通常是外部主动根据具体情况选择了对应的策略(如警察叔叔对象在司机对象吹完酒精检测仪之后,根据结果选择了醉酒驾驶的策略)

状态模式的优缺点:

优点:

  • 将特定状态对应的行为局部化,将不同状态的行为分割开来
  • 将具体的状态改变交由子类来完成,避免了互相之间的依赖

缺点:

  • 具体状态类的增加

猜你喜欢

转载自blog.csdn.net/zhwyj1019/article/details/79789995