《游戏编程模式》一7.4 状态模式

简介:

本节书摘来异步社区《游戏编程模式》一书中的第7章,第7.4节,作者: 【美】Robert Nystrom (尼斯卓姆) 译者: 赵卫兵 , 许新星 , 姜召阳 , 陈侃 , 屈光辉 , 郑炯彬 责编: 陈冀康,更多章节内容可以访问云栖社区“异步社区”公众号查看。

7.4 状态模式

对于熟知面向对象方法的人来说,每一个条件分支都可以用动态分发来解决(换句话说,都可以用C++里面的虚函数来解决)。但是,如果这样做,你可能会把简单问题复杂化。有时候,一个简单的if语句就足够了。

状态模式的由来也有一些历史原因。许多面向对象设计的拥护者—— GoF和重构的作者Martin Fowler都是Smalltalk出身。在那里,如果有一个ifThen语句,我们便可以用一个表示true和false的对象来操作。
但是,在我们这个例子当中,我们发现面对对象设计也就是状态模式更合适。

GoF描述的状态模式在应用到我们的例子中时如下。

7.4.1 一个状态接口

首先,我们为状态定义一个接口。每一个与状态相关的行为都定义成虚函数。在我们的例子中,就是handleInput()和update()函数。

class HeroineState
{
public:
 virtual ~HeroineState() {}
 virtual void handleInput(Heroine& heroine, 
                Input input) {}
 virtual void update(Heroine& heroine) {}
};

7.4.2 为每一个状态定义一个类

对于每一个状态,我们定义了一个类并继承此状态接口。它的方法定义主角对应此状态的行为。换句话说,把之前的switch语句里面的每一个case语句里的内容放置到它们对应的状态类里面去。比如:

class DuckingState : public HeroineState
{
public:
 DuckingState()
 : chargeTime_(0)
 {}

 virtual void handleInput(Heroine& heroine, 
                Input input) {
  if (input == RELEASE_DOWN)
  {
   // Change to standing state...
   heroine.setGraphics(IMAGE_STAND);
  }
 }

 virtual void update(Heroine& heroine) {
  chargeTime_++;
  if (chargeTime_ > MAX_CHARGE)
  {
   heroine.superBomb();
  }
 }

private:
 int chargeTime_;
};

注意,我们这里chargeTime_从Heroine类中移到了DuckingState(躲避状态)类中。这样非常好,因为这个变量只是对躲避状态有意义,现在把它定义在这里,正好显式地反映了我们的对象模型。

7.4.3 状态委托

接下来,我们在主角类中定义一个指针变量,让它指向当前的状态。我们把之前那个很大的switch语句去掉,并让它去调用状态接口的虚函数,最终这些虚方法就会动态地调用具体子状态的相应函数。

状态委托看起来很像策略模式和类型对象模式(第13章)。在这三个模式中,你会有一个主对象委托给另外的附属对象。它们三者的区别主要在于目的不同:

策略模式的目标是将主类与它的部分行为进行解耦。
类型对象模式的目标是使得多个对象通过共享相同类型对象的引用来表现出相似性。
状态模式的目标是通过改变主对象代理的对象来改变主对象的行为。

class Heroine
{
public:
 virtual void handleInput(Input input)
 {
  state_->handleInput(*this, input);
 }

 virtual void update() { state_->update(*this); }

 // Other methods...
private:
 HeroineState* state_;
};

为了修改状态,我们需要把state_指针指向另一个不同的HeroineState状态对象。至此,我们的状态模式就讲完了。

相关文章
|
2月前
|
设计模式 人工智能 监控
C++状态模式探索:从设计到实践的全面指南
C++状态模式探索:从设计到实践的全面指南
42 0
|
20天前
|
设计模式 Java
小谈设计模式(17)—状态模式
小谈设计模式(17)—状态模式
|
5月前
|
设计模式 存储
二十三种设计模式全面解析-揭秘访问者模式:开启对象间灵活交互之门
二十三种设计模式全面解析-揭秘访问者模式:开启对象间灵活交互之门
|
5月前
|
设计模式
二十三种设计模式-解密状态模式:优雅地管理对象状态
二十三种设计模式-解密状态模式:优雅地管理对象状态
|
7月前
|
设计模式 应用服务中间件 uml
解锁设计模式的神秘面纱:编写无懈可击的代码之外观设计模式
解锁设计模式的神秘面纱:编写无懈可击的代码之外观设计模式
26 1
|
10月前
|
设计模式
设计模式再探——状态模式
最近产品中有这样的业务需求,不同时间(这里不是活动的执行时间,而是活动的执行时刻)展示不同的活动;
|
10月前
|
设计模式 算法
设计模式——从简单的程序变化到设计理念
设计模式——从简单的程序变化到设计理念
72 0
|
10月前
|
设计模式 算法
设计模式——组件协作模式之模板方法模式
现代软件专业分工之后的第一个结果是 “框架与应用程序的划分”,“组件协作” 模式通过晚期绑定,来实现框架与应用程序之间的松耦合,是二者之间协作时常用的模式。
56 0
设计模式——组件协作模式之模板方法模式
|
10月前
|
设计模式 缓存 算法
设计模式——组件协作模式之策略模式
现代软件专业分工之后的第一个结果是 “框架与应用程序的划分”,“组件协作” 模式通过晚期绑定,来实现框架与应用程序之间的松耦合,是二者之间协作时常用的模式。
97 0
|
设计模式 前端开发
前端通用编程基础的设计模式之观察者
观察者模式是前端开发中非常常见且实用的一种设计模式。该模式可以帮助我们更好地设计和实现一些复杂的应用程序,例如事件处理、数据绑定以及状态管理等。
93 0