处理状态机中的事件
我的 npc 有一个状态机,其结构如下,
execute state
[[[pred1 pred2....] state1]
[[pred3 pred4....] state2]
[[pred5 pred6....] staten]]
发生的情况是当前状态完成后,它开始迭代状态/谓词列表,一旦谓词列表返回所有 true,它将跳转到状态它与之相关联。
某些事件可能在所有状态下发生,比如玩家命令NPC去某个地方。就像任何其他状态转换一样,我可以检查谓词并更改状态,但向每个状态添加相同的代码似乎有点蹩脚。所以我想知道人们如何处理状态机中的事件?
I have a state machine for my npcs that is structured like the following,
execute state
[[[pred1 pred2....] state1]
[[pred3 pred4....] state2]
[[pred5 pred6....] staten]]
What happens is after current state completes, it starts iterating through the states/predicates list and as soon as a list of predicates that returns all true it will jump to the state that it is associated with.
Certain events can happen during all states, say player commands npc to go somewhere. Just like any other state transition I can check for a predicate and change state but adding the same piece of code to every state seems a bit lame. So I was wondering how people deal with events in state machines?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(4)
当您有一个可以从所有可能状态进行的特定操作时,请像在数学中一样进行:将其因式分解!
即:4*10 + 5*10 + 6*10 + 4*20 + 5*20 + 6*20 = (4+5+6)*(10+20)
即:你的(遗忘)npc 可能正在睡觉,或工作时,或吃饭时。在所有这三种情况下,它都必须对某些事件做出反应(被交谈、被攻击……)。构建两个 FSM:日常活动 = [睡眠、工作、吃饭]。反应状态:{不受干扰、与人交谈、受到攻击、...}。然后将事件仅转发到第二个 FSM
只要您在分解独立的事物,您就可以继续分解 FSM。例如,NPC 的情绪(快乐、中性、愤怒……)与其日常活动及其反应状态无关。我所说的“独立”是指“全国人民代表大会可以工作、交谈、生气,并且不存在矛盾”。当然FSM是互相影响的,被攻击的npc往往会生气。
因此,您可以为 Mood 状态添加第三个 FSM,而不是将其合并到每个节点中
When you have a particular action that can be undertaken from all possible states, do as you would do in mathematics : factor it!
i.e : 4*10 + 5*10 + 6*10 + 4*20 + 5*20 + 6*20 = (4+5+6)*(10+20)
i.e : your (oblivion) npc can be sleeping, or at work, or eating. In all three cases, it must react to some events (be talked to, be attacked, ...). Build two FSM : Daily activity = [sleep, work, eat]. Reaction state : {Undisturbed, Talked to, Attacked, ...}. Then forward the events only to the second FSM
And you can keep on factoring FSM, as long as you're factoring independant things. For example, the mood of the npc (happy, neutral, angry, ...) is independant from it's daily activity and its reaction state. I mean "independant" in the sense "the npc can be at work, talked to, and angry, and there's no contradiction". Of course FSM influence each other, npc that are attacked tend to be angry.
So you could add a third FSM for the Mood state, instead of incorporating it in every single node
使用分层状态机 (HSM)。 HSM 的设计目的正是将常见行为分解为超级状态,并使其可重用于所有子状态。要了解有关 HSM 的更多信息,您可以从 http://en 上的 Wikipedia 文章“UML State Machine”开始。 wikipedia.org/wiki/UML_state_machine。
Use a hierarchical state machine (HSM). HSMs are exactly designed to factor out the common behavior into superstates and make it reusable for all substates. To learn more about HSMs, you can start with the Wikipedia article "UML State Machine" at http://en.wikipedia.org/wiki/UML_state_machine.
只需制作一个如下的数据结构:
顺便说一句,您所概述的看起来不像状态机。在状态机中,下一个状态取决于前一个状态,因此它看起来像:(
条件是您的谓词集)。您还必须以某种方式确保转换是唯一的,即条件 1 和条件 2 不能同时满足。或者取第一个正确的。
Just make a data structure like:
By the way, what you have outlined doesn't look like a state machine. In state machine, next state depends on the previous one, so it would look like:
(condition is your set of predicates). You must also somehow assure that the transition is unique, i.e. that condition1 and condition2 cannot be fulfilled at the same time. Or take the first one which is true.
尝试使用名为“State”的模式 - http://en.wikipedia.org/wiki/State_pattern
定义抽象超类(例如AbsatractState 类,将所有状态通用的方法代码放在那里),所有表示真实状态的类都必须从它派生子类。
Try to use pattern called "State" - http://en.wikipedia.org/wiki/State_pattern
Define abstract superclass (e.g. class AbsatractState, put there code of methods that common for all states), and all classes that represents real states must been subclassed from it.