2010-03-19 55 views
2

结合FSM的状态是否“正确”?组合状态,FSM

说你然而,在FSM理论与

enum State 
{ 
    State1 = 1 << 0, 
    State2 = 1 << 1, 
    State3 = 1 << 2 
} ; 

它碰巧的是,它是有道理的状态结合的对象,如

State myState = State1 | State2 ; 

这是非法的?

它更快捷:

假设你有3种状态:跑步,散步,和跳转。那么你有第四个国家的射击。

你需要能够跑步和射击,步行和射击,跳跃和射击。而不是使6个州RunningFiring,WalkingFiring,JumpingFiring,我想结合与击发状态(无论散步跑步跳跃状态)

我知道我可以只使用一个BOOL的“第四状态”,但这似乎没有人情味? “一边......”

+1

你心里有一个现实世界的例子?通常情况下,像这样的情况表明需要另一个状态...... – Steve 2010-03-19 01:59:43

+0

@Steve:这听起来像是一个答案。请将其发布为答案,以便我们可以正确地对其进行修改。 – 2010-03-19 02:02:45

回答

1

我记得在13岁左右的时候读过一本关于游戏编程的书,并且看到了一个用来模拟属性的位掩码的例子。类似于

const int HAS_WEAPON = 0x1; 
const int WEARING_ARMOR = 0x2; 
const int IS_ALIENT  = 0x4; 

等等。然后你可以将一个NPC的属性表示为一个int,并且可以使用这些属性作为掩码来设置/清除单个位。

现在,当然,由于内存变得更便宜,所以bitpacking不太常见,因此我们可以使用布尔值来表示属性。无论如何,这看起来与你想要做的相似。

但是,属性与状态机中的状态不同。在状态机中,处于一种状态意味着你不一定处于任何其他状态。所以如果你有一堆不相互排斥的东西,那么一个状态机可能不是一个好的选择。考虑到您添加的每个二进制值属性都会使整个机器的大小增加一倍。

当你说

我知道我可以只使用一个BOOL的 “第四态”,但并不似乎 甚至wronger? “在 端的状态。”有一个

它意味着,我认为有可能是你在想,你代表的信息的方式有问题。当然,“射击”听起来像是一个州的好选择,如果你总是在射击或者做别的事情,那么它就像一个状态机一样。但是,如果“射击”可以与现有系统中的所有状态相结合,它是否真的会造成任何伤害,而不是将其建模为属性?

+0

我认为你是正确的,考虑__Firing__作为属性__is__好..即__Firing__是_不是一个状态。 ty为您的答案! – bobobobo 2010-03-19 02:57:51

1

在我看来,当你开始需要结合这样的状态,那么你的状态机开始做的太多了。您可能需要考虑将某些功能/逻辑移动到单独的状态机中,该状态机专注于可能会或可能不会在“父”状态机处于另一状态时更改状态的任务。

+0

它的更多快捷方式 - 请参阅我的编辑 – bobobobo 2010-03-19 02:14:48

+3

这更加强化了我的观点:-)你的“家伙”应该有一个运动状态机,它具有走/跑/跳状态。作为一个单独的模块,他可以有“战术”状态机,它可以负责决定拍摄,防守等。 – 2010-03-19 02:32:26

1

在我看来,这是一个状态的AND分解(以及正常的异或分解)的例子。 UML使用正交区域来模拟这种情况。所以,在这种情况下,你有两个正交区域。第一个包含正常的OR状态Running,Walking和Jumping。另一个正交区域包含状态燃烧。该状态机允许以下组合:运行|射击,步行|射击和跳跃|射击。

您可以用两个状态机来近似这两个正交区域(您需要两个状态变量)。目前,Firing状态机只有一个状态,但我相信你最终会得到互补的状态“not-Firing”,所以它将成为一个合适的状态机。

米罗萨梅克,state-machine.com