资讯专栏INFORMATION COLUMN

设计模式手册之状态模式

call_me_R / 2742人阅读

摘要:什么是状态模式状态模式对象行为是基于状态来改变的。原文地址设计模式手册之状态模式优缺点优点封装了转化规则,对于大量分支语句,可以考虑使用状态类进一步封装。

1. 什么是“状态模式”?
状态模式:对象行为是基于状态来改变的。

内部的状态转化,导致了行为表现形式不同。
所以,用户在外面看起来,好像是修改了行为。

Webpack4系列教程(17篇) + 设计模式手册(16篇):GitHub地址

博客主题推荐:Theme Art Design,“笔记记录+搭建知识体系”的利器。

原文地址: 设计模式手册之状态模式

2. 优缺点

优点

封装了转化规则,对于大量分支语句,可以考虑使用状态类进一步封装。
每个状态都是确定的,所以对象行为是可控的。

缺点

状态模式的关键是将事物的状态都封装成多带带的类,这个类的各种方法就是“此种状态对应的表现行为”。
因此,状态类会增加程序开销

3. 代码实现 3.1 ES6 实现

在JavaScript中,可以直接用JSON对象来代替状态类。

下面代码展示的就是FSM(有限状态机)里面有3种状态:downloadpausedeleted
控制状态转化的代码也在其中。

DownLoad类就是,常说的Context对象,它的行为会随着状态的改变而改变。

const FSM = (() => {
  let currenState = "download";
  return {
    download: {
      click: () => {
        console.log("暂停下载");
        currenState = "pause";
      },
      del: () => {
        console.log("先暂停, 再删除");
      }
    },
    pause: {
      click: () => {
        console.log("继续下载");
        currenState = "download";
      },
      del: () => {
        console.log("删除任务");
        currenState = "deleted";
      }
    },
    deleted: {
      click: () => {
        console.log("任务已删除, 请重新开始");
      },
      del: () => {
        console.log("任务已删除");
      }
    },
    getState: () => currenState
  };
})();

class Download {
  constructor(fsm) {
    this.fsm = fsm;
  }

  handleClick() {
    const { fsm } = this;
    fsm[fsm.getState()].click();
  }

  hanldeDel() {
    const { fsm } = this;
    fsm[fsm.getState()].del();
  }
}

// 开始下载
let download = new Download(FSM);

download.handleClick(); // 暂停下载
download.handleClick(); // 继续下载
download.hanldeDel(); // 下载中,无法执行删除操作
download.handleClick(); // 暂停下载
download.hanldeDel(); // 删除任务
3.2 Python3 实现

python的代码采用的是“面向对象”的编程,没有过度使用函数式的闭包写法(python写起来也不难)。

因此,负责状态转化的类,专门拿出来多带带封装。
其他3个状态类的状态,均由这个状态类来管理。

# 负责状态转化
class StateTransform:
  def __init__(self):
    self.__state = "download"
    self.__states = ["download", "pause", "deleted"]
  
  def change(self, to_state):
    if (not to_state) or (to_state not in self.__states) : 
      raise Exception("state is unvalid")
    self.__state = to_state

  def get_state(self):
    return self.__state

# 以下是三个状态类

class DownloadState: 
  def __init__(self, transfomer):
    self.__state = "download"
    self.__transfomer = transfomer
  
  def click(self):
    print("暂停下载")
    self.__transfomer.change("pause")

  def delete(self):
    print("先暂停, 再删除")
  
class PauseState:
  def __init__(self, transfomer):
    self.__state = "pause"
    self.__transfomer = transfomer
  
  def click(self):
    print("继续下载")
    self.__transfomer.change("download")

  def delete(self):
    print("删除任务")
    self.__transfomer.change("deleted")

class DeletedState:
  def __init__(self, transfomer):
    self.__state = "deleted"
    self.__transfomer = transfomer
  
  def click(self):
    print("任务已删除, 请重新开始")

  def delete(self):
    print("任务已删除")

# 业务代码
class Download:
  def __init__(self):
    self.state_transformer = StateTransform()
    self.state_map = {
      "download": DownloadState(self.state_transformer),
      "pause": PauseState(self.state_transformer),
      "deleted": DeletedState(self.state_transformer)
    }

  def handle_click(self):
    state = self.state_transformer.get_state()
    self.state_map[state].click()
  
  def handle_del(self):
    state = self.state_transformer.get_state()
    self.state_map[state].delete()

if __name__ == "__main__":
  download = Download()
  download.handle_click(); # 暂停下载
  download.handle_click(); # 继续下载
  download.handle_del(); # 下载中,无法执行删除操作
  download.handle_click(); # 暂停下载
  download.handle_del(); # 删除任务
4. 参考

23种设计模式全解析

菜鸟教程状态模式

《JavaScript设计模式与开发实践》

文章版权归作者所有,未经允许请勿转载,若此文章存在违规行为,您可以联系管理员删除。

转载请注明本文地址:https://www.ucloud.cn/yun/109091.html

相关文章

  • 设计模式手册状态模式

    摘要:什么是状态模式状态模式对象行为是基于状态来改变的。原文地址设计模式手册之状态模式优缺点优点封装了转化规则,对于大量分支语句,可以考虑使用状态类进一步封装。 1. 什么是状态模式? 状态模式:对象行为是基于状态来改变的。 内部的状态转化,导致了行为表现形式不同。所以,用户在外面看起来,好像是修改了行为。 Webpack4系列教程(17篇) + 设计模式手册(16篇):GitHub地址 博...

    Faremax 评论0 收藏0
  • 前端每周清单第 51 期: React Context API 与模式变迁, Webpack 与 W

    摘要:前端每周清单第期与模式变迁与优化界面生成作者王下邀月熊编辑徐川前端每周清单专注前端领域内容,以对外文资料的搜集为主,帮助开发者了解一周前端热点分为新闻热点开发教程工程实践深度阅读开源项目巅峰人生等栏目。 showImg(https://segmentfault.com/img/remote/1460000013279448); 前端每周清单第 51 期: React Context A...

    Jiavan 评论0 收藏0
  • Java - 收藏集 - 掘金

    摘要:强大的表单验证前端掘金支持非常强大的内置表单验证,以及。面向对象和面向过程的区别的种设计模式全解析后端掘金一设计模式的分类总体来说设计模式分为三大类创建型模式,共五种工厂方法模式抽象工厂模式单例模式建造者模式原型模式。 强大的 Angular 表单验证 - 前端 - 掘金Angular 支持非常强大的内置表单验证,maxlength、minlength、required 以及 patt...

    XiNGRZ 评论0 收藏0
  • 「码个蛋」2017年200篇精选干货集合

    摘要:让你收获满满码个蛋从年月日推送第篇文章一年过去了已累积推文近篇文章,本文为年度精选,共计篇,按照类别整理便于读者主题阅读。本篇文章是今年的最后一篇技术文章,为了让大家在家也能好好学习,特此花了几个小时整理了这些文章。 showImg(https://segmentfault.com/img/remote/1460000013241596); 让你收获满满! 码个蛋从2017年02月20...

    wangtdgoodluck 评论0 收藏0

发表评论

0条评论

call_me_R

|高级讲师

TA的文章

阅读更多
最新活动
阅读需要支付1元查看
<