設計模式之——狀態模式
物件的行為依賴於它的狀態(屬性),並且可以根據它的狀態改變而改變它的相關行為 ,屬於行為型模式,允許一個物件在其內部狀態改變時改變它的行為
狀態模式是策略模式的孿生兄弟,它們的UML圖是一樣的,但實際上解決的是不同情況的兩種場景問題,工作中用的不多,基本是策略模式比較多
應用場景
- 一個物件的行為取決於它的狀態, 並且它必須在執行時刻根據狀態改變它的行為
- 程式碼中包含大量與物件狀態有關的條件語句 ,比如一個操作中含有龐大的多分支的條件if else語句,且這些分支依賴於該物件的狀態
- 電商訂單狀態:未支付、已支付、派送中,收貨完成等狀態,各個狀態下處理不同的事情
角色
- Context 上下文:定義了客戶程式需要的介面並維護一個具體狀態角色的例項,將與狀態相關的操作委託給當前的Concrete State物件來處理
- State 抽象狀態類: 定義一個介面以封裝與Context的一個特定狀態相關的行為
- ConcreteState具體狀態類: 實現抽象狀態定義的介面
程式碼實現
以電商訂單狀態流轉為例,每步都有不同的操作內容: 新建訂單/已支付/已發貨/確認收貨
public interface State {
void handle();
}
介面實現
public class NewOrderState implements State{
@Override
public void handle() {
System.out.println("新訂單,未支付");
System.out.println("呼叫商戶客服服務,有新訂單\n");
}
}
public class PayOrderState implements State{
@Override
public void handle() {
System.out.println("新訂單已經支付");
System.out.println("呼叫商戶客服服務,訂單已經支付");
System.out.println("呼叫物流服務,未發貨\n");
}
}
public class SendOrderState implements State{
@Override
public void handle() {
System.out.println("訂單已經發貨");
System.out.println("呼叫簡訊服務,告訴使用者已經發貨");
System.out.println("更新物流資訊\n");
}
}
public class OrderContext {
private State state;
public OrderContext(){}
public void setState(State state) {
this.state = state;
System.out.println("訂單狀態變更!!");
this.state.handle();
}
}
測試
public static void main(String[] args) {
OrderContext orderContext = new OrderContext();
orderContext.setState(new NewOrderState());
orderContext.setState(new PayOrderState());
orderContext.setState(new SendOrderState());
}
優點
1、結構清晰:將狀態類獨立為類,消除了冗餘的if...else 或 switch...case 語句,使程式碼更加簡潔,提高系統可維護性
2、將狀態轉換顯示化:通常的物件內部都是使用數值型別來定義狀態,狀態的切換是通過賦值進行表現,不夠直觀;而使用狀態類,在切換時,是以不同的類進行表示,轉換目的更加明確
3、狀態類職責明確且具備擴充套件性
缺點
1、類膨脹:如果一個事物具備很多狀態,則會造成狀態類太多
2、狀態模式的結構與實現都較為複雜,如果使用不當將導致程式結構和程式碼的婚禮
3、狀態模式對開閉原則的支援並不太好,對於可以切換狀態的狀態模式,增加新的狀態類需要修改那些負責狀態轉換的原始碼,否則無法切換到新增狀態,而且修改某個狀態類的行為也需要修改對應類的原始碼
相關文章
- PHP 設計模式之狀態模式PHP設計模式
- 設計模式20之狀態模式設計模式
- 設計模式之狀態模式(State)設計模式
- C#設計模式之狀態模式C#設計模式
- 設計模式漫談之狀態模式設計模式
- 設計模式:狀態模式設計模式
- 設計模式-狀態模式設計模式
- 折騰Java設計模式之狀態模式Java設計模式
- Unity【話大】設計模式之狀態模式Unity設計模式
- python設計模式狀態模式Python設計模式
- 設計模式(十五)狀態模式設計模式
- 設計模式之策略模式和狀態模式(strategy pattern & state pattern)設計模式
- 設計模式(二十一)----行為型模式之狀態模式設計模式
- 設計模式-狀態模式(State Pattern)設計模式
- 《Head First 設計模式》:狀態模式設計模式
- 簡說設計模式——狀態模式設計模式
- 極簡設計模式-狀態模式設計模式
- GoLang設計模式14 - 狀態模式Golang設計模式
- python設計模式【9】-狀態模式Python設計模式
- 設計模式之狀態模式(三分鐘學會一個設計模式)設計模式
- 23種設計模式(七)-狀態設計模式設計模式
- 設計模式第八講-狀態模式設計模式
- 設計模式--直譯器模式和狀態模式設計模式
- Java進階篇設計模式之十二 ---- 備忘錄模式和狀態模式Java設計模式
- 用設計模式去掉沒必要的狀態變數 —— 狀態模式設計模式變數
- 行為型設計模式 - 狀態模式詳解設計模式
- 無廢話設計模式(14)結構型模式--狀態模式設計模式
- 《設計模式七》備忘錄、模板方法、狀態模式及設計模式設計總結設計模式
- 《JavaScript設計模式與開發實踐》模式篇(13)—— 狀態模式JavaScript設計模式
- 23種設計模式之——動態代理模式設計模式
- 軟體設計模式系列之二十二——狀態模式設計模式
- 軟體設計模式學習(二十四)狀態模式設計模式
- 23種設計模式之代理模式(靜態代理)設計模式
- 設計模式學習筆記(二十)狀態模式及其實現設計模式筆記
- 設計模式 第十章 備忘錄模式、直譯器模式、狀態模式設計模式
- 設計模式之cglib動態代理設計模式CGLib
- 設計模式之策略模式設計模式
- 設計模式之代理模式設計模式