博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
设计模式-状态模式
阅读量:4163 次
发布时间:2019-05-26

本文共 5136 字,大约阅读时间需要 17 分钟。

文章目录

模式介绍

如果我们在编写代码的时候,遇到大量的条件判断的时候,可能会采用策略模式来优化结构,因为这时涉及到策略的选择,但有时候仔细查看下,就会发现,这些所谓的策略其实是对象的不同状态,更加明显的是,对象的某种状态也成为判断的条件

实例

一个类对外提供了多个行为,同时该类对象有多种状态,不同状态下对外的行为的表现不同,比如无人自动咖啡售卖机开发一个控制程序。

用户可以再咖啡机上进行支付、退款、购买、取咖啡操作

不同状态下,这四种操作将有不同的表现。比如在没有支付的状态下,用户在咖啡机上点退款、购买、取咖啡,和在已支付的状态下做着三个操作时不一样的。

在这里插入图片描述
面对这样的需求,你可能会写出这样的代码:

public class CoffeeMachine {
final static int NO_PAY = 0; final static int PAY = 1; final static int SOLD = 2; final static int SOLD_OUT = 4; private int state = SOLD_OUT; private int store; public CoffeeMachine(int store) {
this.store = store; if (this.store > 0) {
this.state = NO_PAY; } } public void pay() {
switch (this.state) {
case NO_PAY: System.out.println("支付成功,请确定购买咖啡。"); this.state = PAY; break; case PAY: System.out.println("已支付成功,请确定购买咖啡。"); break; case SOLD: System.out.println("待取咖啡中,请稍后购买!"); break; case SOLD_OUT: System.out.println("咖啡已售罄,不可购买!"); } } public void refund() {
switch (this.state) {
case NO_PAY: System.out.println("你尚未支付,请不要乱按!"); break; case PAY: System.out.println("退款成功!"); this.state = NO_PAY; break; case SOLD: System.out.println("已购买,请取用!"); break; case SOLD_OUT: System.out.println("咖啡已售罄,不可购买!"); } } // 购买 public void buy() {
switch (this.state) {
case NO_PAY: System.out.println("你尚未支付,请不要乱按!"); break; case PAY: System.out.println("购买成功,请取用!"); this.state = SOLD; break; case SOLD: System.out.println("已购买,请取用!"); break; case SOLD_OUT: System.out.println("咖啡已售罄,不可购买!"); } } // 取coffee public void getCoffee() {
switch (this.state) {
case NO_PAY: System.out.println("你尚未支付,请不要乱按!"); break; case PAY: System.out.println("已购买,请取用!"); break; case SOLD: System.out.println("请放好杯子,3秒后将出咖啡!"); this.store--; if (this.store == 0) {
this.state = SOLD_OUT; } else {
this.state = NO_PAY; } break; case SOLD_OUT: System.out.println("咖啡已售罄,不可购买!"); } }}

这种写法,如果新增一种状态或者改变状态的行为,那么改动特别大,极其难以维护,因此我们接下来使用状态模式来解决这个问题

模式类图

在这里插入图片描述

代码实例

改进上面的例子,使用状态模式

咖啡机代码:

public class NewCoffeeMachine {
final State NO_PAY, PAY, SOLD, SOLD_OUT; State state; int store; public NewCoffeeMachine(int store) {
NO_PAY = new NoPayState(this); PAY = new PayState(this); SOLD = new SoldState(this); SOLD_OUT = new SoldOutState(this); this.store = store; if (this.store > 0) {
this.state = NO_PAY; } } public void pay() {
this.state.pay(); } public void refund() {
this.state.refund(); } public void buy() {
this.state.buy(); } public void getCoffee() {
this.state.getCoffee(); }}

状态接口类:

public interface State {
void pay(); void refund(); void buy(); void getCoffee();}

未支付状态实现类:

public class NoPayState implements State {
private NewCoffeeMachine machine; public NoPayState(NewCoffeeMachine machine) {
this.machine = machine; } @Override public void pay() {
System.out.println("支付成功,请去确定购买咖啡。"); this.machine.state = this.machine.PAY; } @Override public void refund() {
System.out.println("你尚未支付,请不要乱按!"); } @Override public void buy() {
System.out.println("你尚未支付,请不要乱按!"); } @Override public void getCoffee() {
System.out.println("你尚未支付,请不要乱按!"); }}

支付状态实现类:

public class PayState implements State {
private NewCoffeeMachine machine; public PayState(NewCoffeeMachine machine) {
this.machine = machine; } @Override public void pay() {
System.out.println("您已支付,请去确定购买!"); } @Override public void refund() {
System.out.println("退款成功,请收好!"); this.machine.state = this.machine.NO_PAY; } @Override public void buy() {
System.out.println("购买成功,请取用"); this.machine.state = this.machine.SOLD; } @Override public void getCoffee() {
System.out.println("请先确定购买!"); }}

售出状态实现类:

public class SoldState implements State {
private NewCoffeeMachine machine; public SoldState(NewCoffeeMachine machine) {
this.machine = machine; } @Override public void pay() {
} @Override public void refund() {
// TODO Auto-generated method stub } @Override public void buy() {
// TODO Auto-generated method stub } @Override public void getCoffee() {
// TODO Auto-generated method stub }}

售罄状态实现类:

public class SoldOutState implements State {
private NewCoffeeMachine machine; public SoldOutState(NewCoffeeMachine machine) {
this.machine = machine; } @Override public void pay() {
} @Override public void refund() {
// TODO Auto-generated method stub } @Override public void buy() {
// TODO Auto-generated method stub } @Override public void getCoffee() {
// TODO Auto-generated method stub }}

总结

  • 要使用状态模式,我们必须明确两个东西:状态和每个状态下执行的动作
  • 在状态模式中,因为所有的状态都要执行相应的动作,所以我们可以考虑将状态抽象出来
  • 状态的抽象一般有两种形式:接口和抽象类。如果所有的状态都有共同的数据域,可以使用抽象类,但如果只是单纯的执行动作,就可以使用接口
  • 状态模式的好处就是将我们从这个复杂的嵌套条件中脱离出来,但状态模式的坏处也是非常明显:需要管理一系列的状态类
  • 策略模式侧重的是一个行为的多个算法实现,可互换算法;命令模式侧重的是为多个行为提供灵活的执行方式;状态模式,应用于状态机的情况

转载地址:http://lwpxi.baihongyu.com/

你可能感兴趣的文章
Online Multi-Object Tracking via Structural Constraint Event Aggregation
查看>>
The Solution Path Algotithm for Identity-Aware Multi-Object Tracking
查看>>
Groupwise Tracking of Crowded Similar-Appearance Targets from Low-Continuity Image Sequences
查看>>
CDTS: Collaborative Detection, Tracking, and Segmentation for Online Multiple Object Segmentation
查看>>
Deep Network Flow for Multi-Object Tracking
查看>>
Multiple People Tracking by Lifted Multicut and Person Re-identification
查看>>
Multi-Object Tracking with Quadruplet Convolutional Neural Networks
查看>>
关于多目标跟踪的一点理解
查看>>
Learning by tracking:Siamese CNN for robust target association
查看>>
MUSTer:Multi-Store Tracker:A Cognitive Psychology Inspired Approach to Object Tracking
查看>>
Understanding and Diagnosing Visual Tracking Systems
查看>>
Multiple People Tracking by Lifted Multicut and Person Re-identification
查看>>
Visual Tracking Using Attention-Modulated Disintegration and Integration
查看>>
Action-Decision Networks for Visual Tracking with Deep Reinforcement Learning
查看>>
Multiple Object Tracking with High Performance Detection and Appearance Feature
查看>>
深度学习入门(上)-第一章 必备基础知识点
查看>>
ubuntu unzip解压时提示错误 解决方法
查看>>
sprintf函数的说明
查看>>
BOOST_TYPEOF和BOOST_AUTO 作用
查看>>
随机森林概述
查看>>