简介
对象的行为依赖于它的状态(属性),可以根据状态的改变而改变相关行为。
UML图:
应用场景:
- 对象的行为取决于其状态,并且必须要在运行时刻根据状态而改变行为
- 代码中包含大量与对象状态有关的条件语句
示例
上午、下午、晚上工作的状态
- 上下文对象:
public class Work {/*** 工作状态*/private State state;/*** 当前时间*/private int hour;/*** 工作是否完成*/private boolean isFinished;public Work() {// 初始化操作this.state = new MorningState();}public void writeProgram() {state.writeProgram(this);}public State getState() {return state;}public void setState(State state) {this.state = state;}public int getHour() {return hour;}public void setHour(int hour) {this.hour = hour;}public boolean isFinished() {return isFinished;}public void setFinished(boolean finished) {isFinished = finished;}
}
- 状态
public interface State {void writeProgram(Work work);
}
public class MorningState implements State {@Overridepublic void writeProgram(Work work) {if (work.getHour() < 12) {System.out.println("当前时间:" + work.getHour() + ",干劲十足!");} else {work.setState(new NoonState());work.writeProgram();}}
}
public class NoonState implements State {@Overridepublic void writeProgram(Work work) {if (work.getHour() < 13) {System.out.println("当前时间:" + work.getHour() + ",好饿,开始干饭!");} else {work.setState(new AfternoonState());work.writeProgram();}}
}
public class AfternoonState implements State {@Overridepublic void writeProgram(Work work) {if (work.getHour() < 18) {System.out.println("当前时间:" + work.getHour() + ",开始上班,有点疲惫!");} else {work.setState(new EveningState());work.writeProgram();}}
}
public class EveningState implements State {@Overridepublic void writeProgram(Work work) {if (!work.isFinished()) {System.out.println("当前时间:" + work.getHour() + ",又要加班");} else {System.out.println("当前时间:" + work.getHour() + ",下班啦!");}}
}
- 运行
public class Main {public static void main(String[] args) {Work work = new Work();// 上午work.setHour(9);work.writeProgram();// 中午work.setHour(12);work.writeProgram();// 下午work.setHour(16);work.writeProgram();// 晚上work.setHour(18);
// work.setFinished(true);work.writeProgram();}
}
总结
- 优点
- 只需改变对象的状态,就可改变对象的行为
- 多个环境对象共享一个状态对象,可以减少系统中对象的个数
- 缺点
- 增加系统类和对象的个数
- 使用不当将造成程序结构和代码的混乱
- 不符合开闭原则,新增状态需要修改源码
VS 策略模式
- 状态模式重在各个状态之间的切换从而有不同的行为,策略模式重在根据具体情况选择策略不涉及状态的切换
- 状态模式不同状态做不同的事情且不能相互替换,策略模式解决的都是同一件事