設計模式狀態模式 ( 簡介 | 適用場景 | 優缺點 | 代碼示例 )

      網友投稿 630 2022-05-30

      文章目錄

      一、狀態模式簡介

      二、狀態模式適用場景

      三、狀態模式優缺點

      四、狀態模式相關設計模式

      五、狀態模式代碼示例

      1、狀態類父類

      2、播放狀態類

      3、暫停狀態類

      4、快進狀態類

      5、停止狀態類

      6、上下文控制類

      7、測試

      一、狀態模式簡介

      狀態模式 : 允許 對象 在

      內部狀態 改變時 ,

      改變它的行為 ;

      一個對象 , 如果其

      內部狀態改變

      , 其

      行為也需要進行改變

      ; 如果其行為不需要改變 , 也可以只

      控制 該對象的狀態 的 互相轉換 ;

      當控制一個對象 , 其狀態轉換過程比較復雜時 , 將

      狀態判斷邏輯 ,

      轉到代表不同狀態的一系列類中 ;

      如 : 引入 視頻播放 的業務場景 , 播放器有 初始狀態 , 播放狀態 , 暫停狀態 , 停止狀態 , 快進狀態 等多種狀態 , 將這些

      狀態

      都封裝到

      代表不同狀態的類

      中 , 可以將復雜的判斷邏輯簡化 , 將這些

      邏輯

      擴展到不同的狀態類中 ;

      狀態模式類型 : 行為型 ;

      二、狀態模式適用場景

      狀態模式適用場景 : 一個對象 ,

      存在多個狀態 ,

      狀態可以相互轉換 ;

      不同狀態下 ,

      行為不同 ;

      不同狀態下 , 行為不同的示例 , 如 :

      購買物品 , 將物品放入購物車并生成訂單 , 可以進行付款 ; 如果 訂單 超過 24 小時后 , 被關閉訂單 , 此時訂單取消 , 無法付款 ;

      電梯運行時 , 不能開門 ; 電梯停止后 , 才能開門 ;

      三、狀態模式優缺點

      狀態模式優點 :

      可以將

      不同的狀態

      隔離

      ; 每個狀態都是一個單獨的類 ;

      可以將 各種狀態 的

      轉換邏輯

      ,

      分布到 狀態 的子類中 ,

      減少相互依賴 ;

      增加 新狀態 , 操作簡單 ;

      狀態模式缺點 :

      如果

      狀態數量 比較多

      ,

      狀態類 的 數量會增加

      ,

      業務場景系統變得很復雜

      ; 如果業務中某個對象由幾十上百個狀態 , 就會很復雜 , 這時就需要對狀態進行拆分處理 ;

      四、狀態模式相關設計模式

      狀態模式 與 享元模式 , 可以配合在一起使用 , 可以使用享元模式 ,

      在多個上下文中 ,

      共享狀態實例 ;

      五、狀態模式代碼示例

      業務場景 :

      視頻播放器 , 有 : 暫停 , 播放 , 快進 , 停止 , 四個狀態 ;

      在 停止 狀態下 , 無法快進 , 如果當前是 停止 狀態 , 此時要轉為 快進 狀態 , 需要進行校驗 ;

      如果不使用 狀態模式 , 則需要進行 if else 判斷 ;

      如果使用 狀態模式 , 就很容易實現 ;

      狀態類 :

      定義狀態父類抽象類 , 抽象方法是各個狀態對應的方法 ;

      定義狀態子類 , 每個狀態對應一個子類對象 ;

      上下文類 :

      在該類中封裝 所有的狀態實例 , 以及定義 狀態改變方法 ;

      封裝當前狀態類 , 狀態改變方法 調用時 , 實際上調用的是 當前狀態類的 對應方法 ;

      1、狀態類父類

      package state; /** * 視頻狀態 父類 * 所有的視頻狀態 , 都要繼承該類 */ public abstract class VedioState { /** * 視頻播放上下文 * 聲明為 protected , 子類可以拿到該成員變量 */ protected VedioContext vedioContext; public void setVedioContext(VedioContext vedioContext) { this.vedioContext = vedioContext; } /** * 播放 * 對應播放狀態 */ public abstract void play(); /** * 停止 * 對應停止狀態 */ public abstract void pause(); /** * 快進 * 對應快進狀態 */ public abstract void speed(); /** * 停止 * 對應停止狀態 */ public abstract void stop(); }

      1

      2

      3

      4

      5

      6

      7

      8

      9

      10

      11

      12

      13

      14

      15

      16

      17

      【設計模式】狀態模式 ( 簡介 | 適用場景 | 優缺點 | 代碼示例 )

      18

      19

      20

      21

      22

      23

      24

      25

      26

      27

      28

      29

      30

      31

      32

      33

      34

      35

      36

      37

      38

      39

      40

      41

      42

      2、播放狀態類

      package state; /** * 視頻的播放狀態 * 可以進行 快進 , 暫停 , 停止 操作 */ public class PlayState extends VedioState{ @Override public void play() { System.out.println("正常播放視頻"); } /** * 暫停時 , 只需要調用 PlayState 父類 VedioState 的上下文 VedioContext * 將上下文 VedioContext 中的狀態 , 設置為 暫停 的狀態即可 */ @Override public void pause() { super.vedioContext.setVedioState(VedioContext.PAUSE_STATE); } /** * 快進時 , 只需要調用 PlayState 父類 VedioState 的上下文 VedioContext * 將上下文 VedioContext 中的狀態 , 設置為 快進 的狀態即可 */ @Override public void speed() { super.vedioContext.setVedioState(VedioContext.SPEED_STATE); } /** * 停止時 , 只需要調用 PlayState 父類 VedioState 的上下文 VedioContext * 將上下文 VedioContext 中的狀態 , 設置為 停止 的狀態即可 */ @Override public void stop() { super.vedioContext.setVedioState(VedioContext.STOP_STATE); } }

      1

      2

      3

      4

      5

      6

      7

      8

      9

      10

      11

      12

      13

      14

      15

      16

      17

      18

      19

      20

      21

      22

      23

      24

      25

      26

      27

      28

      29

      30

      31

      32

      33

      34

      35

      36

      37

      38

      39

      40

      3、暫停狀態類

      package state; /** * 視頻暫停狀態 * 暫停狀態 可以 切換到 播放 , 快進 , 停止 狀態 */ public class PauseState extends VedioState{ /** * 播放時 , 只需要調用 PlayState 父類 VedioState 的上下文 VedioContext * 將上下文 VedioContext 中的狀態 , 設置為 播放 的狀態即可 */ @Override public void play() { super.vedioContext.setVedioState(VedioContext.PLAY_STATE); } /** * 暫停時 , 只需要調用 PlayState 父類 VedioState 的上下文 VedioContext * 將上下文 VedioContext 中的狀態 , 設置為 暫停 的狀態即可 */ @Override public void pause() { System.out.println("暫停播放視頻"); } /** * 快進時 , 只需要調用 PlayState 父類 VedioState 的上下文 VedioContext * 將上下文 VedioContext 中的狀態 , 設置為 快進 的狀態即可 */ @Override public void speed() { super.vedioContext.setVedioState(VedioContext.SPEED_STATE); } /** * 停止時 , 只需要調用 PlayState 父類 VedioState 的上下文 VedioContext * 將上下文 VedioContext 中的狀態 , 設置為 停止 的狀態即可 */ @Override public void stop() { super.vedioContext.setVedioState(VedioContext.STOP_STATE); } }

      1

      2

      3

      4

      5

      6

      7

      8

      9

      10

      11

      12

      13

      14

      15

      16

      17

      18

      19

      20

      21

      22

      23

      24

      25

      26

      27

      28

      29

      30

      31

      32

      33

      34

      35

      36

      37

      38

      39

      40

      41

      42

      43

      44

      4、快進狀態類

      package state; /** * 視頻快進狀態 * 快進狀態下 , 可以進行 播放 , 暫停 , 停止操作 */ public class SpeedState extends VedioState{ /** * 播放時 , 只需要調用 PlayState 父類 VedioState 的上下文 VedioContext * 將上下文 VedioContext 中的狀態 , 設置為 播放 的狀態即可 */ @Override public void play() { super.vedioContext.setVedioState(VedioContext.PLAY_STATE); } /** * 暫停時 , 只需要調用 PlayState 父類 VedioState 的上下文 VedioContext * 將上下文 VedioContext 中的狀態 , 設置為 暫停 的狀態即可 */ @Override public void pause() { System.out.println("快進播放視頻"); } /** * 快進時 , 只需要調用 PlayState 父類 VedioState 的上下文 VedioContext * 將上下文 VedioContext 中的狀態 , 設置為 快進 的狀態即可 */ @Override public void speed() { super.vedioContext.setVedioState(VedioContext.SPEED_STATE); } /** * 停止時 , 只需要調用 PlayState 父類 VedioState 的上下文 VedioContext * 將上下文 VedioContext 中的狀態 , 設置為 停止 的狀態即可 */ @Override public void stop() { super.vedioContext.setVedioState(VedioContext.STOP_STATE); } }

      1

      2

      3

      4

      5

      6

      7

      8

      9

      10

      11

      12

      13

      14

      15

      16

      17

      18

      19

      20

      21

      22

      23

      24

      25

      26

      27

      28

      29

      30

      31

      32

      33

      34

      35

      36

      37

      38

      39

      40

      41

      42

      43

      44

      5、停止狀態類

      package state; /** * 視頻的停止狀態 * 可以進行 播放 操作 * 不能進行 快進 , 暫停 操作 */ public class StopState extends VedioState{ /** * 播放時 , 只需要調用 PlayState 父類 VedioState 的上下文 VedioContext * 將上下文 VedioContext 中的狀態 , 設置為 播放 的狀態即可 */ @Override public void play() { super.vedioContext.setVedioState(VedioContext.PLAY_STATE); } /** * 不能暫停 */ @Override public void pause() { System.out.println("停止狀態不能暫停"); } /** * 不能快進 */ @Override public void speed() { System.out.println("停止狀態不能快進"); } /** * 停止時 , 只需要調用 PlayState 父類 VedioState 的上下文 VedioContext * 將上下文 VedioContext 中的狀態 , 設置為 停止 的狀態即可 */ @Override public void stop() { System.out.println("停止播放視頻"); } }

      1

      2

      3

      4

      5

      6

      7

      8

      9

      10

      11

      12

      13

      14

      15

      16

      17

      18

      19

      20

      21

      22

      23

      24

      25

      26

      27

      28

      29

      30

      31

      32

      33

      34

      35

      36

      37

      38

      39

      40

      41

      42

      43

      6、上下文控制類

      package state; /** * 使用享元模式 , 共享同一個對象 * * 上下文也有 play , pause , speed , stop 等狀態 * 執行這些方法時 , 調用狀態的相應方法 */ public class VedioContext { /** * 當前的狀態 */ private VedioState mVedioState; public final static PlayState PLAY_STATE = new PlayState(); public final static PauseState PAUSE_STATE = new PauseState(); public final static SpeedState SPEED_STATE = new SpeedState(); public final static StopState STOP_STATE = new StopState(); public VedioState getVedioState() { return mVedioState; } /** * 將傳入的 VedioState , 賦值給當前的 VedioState mVedioState 成員 * 除此之外 , 還要設置 VedioState 的上下文 , 即該類本身 * 將當前的環境 VedioContext , 通知到各個狀態實現類 * @param mVedioState */ public void setVedioState(VedioState mVedioState) { this.mVedioState = mVedioState; this.mVedioState.setVedioContext(this); } public void play() { this.mVedioState.play(); } public void pause() { this.mVedioState.pause(); } public void speed() { this.mVedioState.speed(); } public void stop() { this.mVedioState.stop(); } }

      1

      2

      3

      4

      5

      6

      7

      8

      9

      10

      11

      12

      13

      14

      15

      16

      17

      18

      19

      20

      21

      22

      23

      24

      25

      26

      27

      28

      29

      30

      31

      32

      33

      34

      35

      36

      37

      38

      39

      40

      41

      42

      43

      44

      45

      46

      47

      48

      49

      50

      51

      7、測試

      package state; public class Main { public static void main(String[] args) { VedioContext vedioContext = new VedioContext(); vedioContext.setVedioState(VedioContext.PLAY_STATE); System.out.println("當前視頻狀態 : " + vedioContext.getVedioState().getClass().getSimpleName()); vedioContext.pause(); System.out.println("當前視頻狀態 : " + vedioContext.getVedioState().getClass().getSimpleName()); vedioContext.speed(); System.out.println("當前視頻狀態 : " + vedioContext.getVedioState().getClass().getSimpleName()); vedioContext.stop(); System.out.println("當前視頻狀態 : " + vedioContext.getVedioState().getClass().getSimpleName()); vedioContext.speed(); System.out.println("當前視頻狀態 : " + vedioContext.getVedioState().getClass().getSimpleName()); } }

      1

      2

      3

      4

      5

      6

      7

      8

      9

      10

      11

      12

      13

      14

      15

      16

      17

      18

      19

      20

      21

      22

      執行結果 :

      視頻

      版權聲明:本文內容由網絡用戶投稿,版權歸原作者所有,本站不擁有其著作權,亦不承擔相應法律責任。如果您發現本站中有涉嫌抄襲或描述失實的內容,請聯系我們jiasou666@gmail.com 處理,核實后本網站將在24小時內刪除侵權內容。

      上一篇:【Java】String類字符串的解析
      下一篇:移動辦公OA會議管理方案:大、小會議輕松管,高效開
      相關文章
      亚洲大尺度无码专区尤物| 久久精品亚洲日本波多野结衣| 亚洲国产人成在线观看69网站| 亚洲综合国产成人丁香五月激情| 午夜亚洲国产理论秋霞| 国产成人亚洲影院在线观看| 一区二区亚洲精品精华液| 亚洲免费观看网站| 亚洲一级毛片在线观| 亚洲一级高清在线中文字幕| 亚洲区精品久久一区二区三区| 九月丁香婷婷亚洲综合色| 久久亚洲精品视频| 亚洲av中文无码乱人伦在线播放| 亚洲精品国偷自产在线| 亚洲高清国产拍精品26U| 亚洲av无码不卡| 亚洲综合婷婷久久| 亚洲精品国产手机| 亚洲mv国产精品mv日本mv| 亚洲中文字幕乱码一区| 亚洲GV天堂GV无码男同| 一本色道久久综合亚洲精品蜜桃冫| 亚洲人成人无码.www石榴| 亚洲乱亚洲乱妇无码| 久久亚洲中文无码咪咪爱| 亚洲高清成人一区二区三区| 午夜亚洲av永久无码精品| 国产国拍亚洲精品福利 | 久久久久亚洲Av无码专| 亚洲黄网在线观看| 亚洲图片中文字幕| 中文文字幕文字幕亚洲色| 亚洲中文字幕无码爆乳app| 亚洲第一se情网站| 在线观看亚洲精品福利片| 亚洲爆乳无码一区二区三区| 亚洲精品无码国产| 一区二区三区亚洲| 国产v亚洲v天堂a无| 99亚洲乱人伦aⅴ精品|