類圖
定義
當一個對象內在狀態改變時允許其改變行爲,這個對象看起來像改變了其類
優點
- 結構清晰
- 遵循設計原則。很好的體現了開閉原則和單一職責原則
- 封裝性非常好缺點
- 子類會很多,每個狀態都有一個子類
使用場景
- 行爲隨狀態改變而改變的場景
- 條件,分支判斷語句的替代者
注意事項
狀態模式適用於當某個對象在它的狀態發生改變時,它的行爲隨着發生比較大的變化,即行爲受狀態約束的情況下可以使用狀態模式
抽象狀態角色
public abstract class State {
/**
* 定義一個環境角色,提供子類訪問
*/
protected Context context;
public Context getContext() {
return context;
}
public void setContext(Context context) {
this.context = context;
}
public abstract void handle1();
public abstract void handle2();
}
具體狀態角色1
public class ConcreteState1 extends State {
@Override
public void handle1() {
// 改狀態下必須處理的邏輯
System.out.println("ConcreteState1->handle1()");
}
@Override
public void handle2() {
System.out.println("狀態轉換");
// 設置當前狀態爲state2
super.context.setCurrentState(Context.STATE2);
// 過渡到state2狀態,由Context實現
super.context.handle2();
}
@Override
public String toString() {
return "狀態1";
}
}
具體狀態角色2
public class ConcreteState2 extends State {
@Override
public void handle1() {
System.out.println("狀態轉換");
super.context.setCurrentState(Context.STATE1);
super.context.handle1();
}
@Override
public void handle2() {
System.out.println("ConcreteState2->handle2()");
}
@Override
public String toString() {
return "狀態2";
}
}
具體環境角色
public class Context {
public final static State STATE1 = new ConcreteState1();
public final static State STATE2 = new ConcreteState2();
/**
* 當前狀態
*/
private State currentState;
/**
* 獲取當前狀態
*
* @return
*/
public State getCurrentState() {
return currentState;
}
/**
* 定義狀態
*
* @param currentState
*/
public void setCurrentState(State currentState) {
this.currentState = currentState;
this.currentState.setContext(this);
}
/**
* 行爲委託
*/
public void handle1() {
this.currentState.handle1();
}
public void handle2() {
this.currentState.handle2();
}
}
場景類
public class Client {
public static void main(String[] args) {
//定義環境角色
Context context = new Context();
//初始化狀態
context.setCurrentState(new ConcreteState1());
System.out.println("當前狀態:"+context.getCurrentState());
//行爲委託
context.handle1();
System.out.println("當前狀態:"+context.getCurrentState());
context.handle2();
System.out.println("當前狀態:"+context.getCurrentState());
}
}
運行結果
當前狀態:狀態1
ConcreteState1->handle1()
當前狀態:狀態1
狀態轉換
ConcreteState2->handle2()
當前狀態:狀態2