事物的状态-状态模式


title: 事物的状态-状态模式
date: 2018-09-05 16:11:35
categories:

  • 工作
    tags:
  • Java

前段时间看到有代码在用状态机,而这段时间重温软件设计模式,刚好有状态模式,记录一下。

场景:

对于一个自动售卖机的小系统,往往会有,投币、售出、售罄、退钱等状态。状态之间需要转换,才能完成一系列操作,实现某一个完整的功能。

糟糕的解决方案

旧的解决方案是怎样的呢?
首先,用常量定义出所有状态。
在进行操作时,用if判断当前状态是否是定义出来的某个状态,然后进行相应的操作。同时进行状态的切换。

问题点:

用上述方法解决的问题,会有如下痛点:

  1. 扩展性极差,如果新增一个状态,需要变动原有逻辑代码,严重违反【对扩展开放】的原则。
  2. 随着时间流逝,主流程出现大量的if判断,导致某个方法过于庞大,不利于阅读维护。
  3. 完全是面向过程思维方式,不是面向对象的思考方式。

改良的解决方案

切入点:将每个状态的行为放在对应的状态类中,每个状态只要实现自己的动作就可以了。
思路:

  1. 定义一个状态接口(or 抽象类)。每个动作在接口中都有对应的方法。
  2. 每个具体的状态实现状态接口,并负责自己当前状态下各个方法的实现,eg:售出状态的退钱方法,取东西方法等。
  3. 最后,主流程里将动作委托给对应的状态类。

类图如下

image-20190914221223233

如图1状态模式类图所示,State是定义状态动作的接口,ConcreteStateA与ConcreteStateB是接口State的具体状态。Context是上下文中进行调用,调用State.handle方法,用多态代替了if。

在具体使用过程中,ConcreteStateA与ConcreteStateB或其他状态可以相互转换,也可以在Context中转换。同时,当遇到拓展时,比如新增状态ConcreteStateC,只需要新增ConcreteStateC实现State接口,完成handle,并在Context里进行调用。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值