其他分享
首页 > 其他分享> > c – 状态机表示

c – 状态机表示

作者:互联网

我想将GUI实现为状态机.我认为这样做有一些好处和一些缺点,但这不是这个问题的主题.

在对此进行一些阅读之后,我发现了几种用C建模状态机的方法,我坚持使用2,但我不知道哪种方法更适合GUI建模.

>使用以下方法将State Machine表示为状态列表:

> OnEvent(…);
> OnEnterState(…);
> OnExitState(…);

从StateMachine :: OnEvent(…)我将事件转发到CurrentState :: OnEvent(…),这里决定是否进行转换.在转换时,我调用CurrentState :: OnExitState(…),NewState :: OnEnterState()和CurrentState = NewState;

通过这种方法,状态将与动作紧密耦合,但是当从一个状态我可以进入多个状态并且我必须针对不同的转换采取不同的动作时状态可能变得复杂.
>将状态机表示为具有以下属性的转换列表:

> InitialState
> FinalState
> OnEvent(…)
> DoTransition(…)

从StateMachine :: OnEvent(…)我将事件转发到所有转换,其中InitialState与状态机中的CurrentState具有相同的值.如果满足转换条件,则停止循环,调用DoTransition方法并将CurrentState设置为Transition :: FinalState.

使用这种方法,转换将非常简单,但转换计数的数量可能会非常高.此外,当一个州收到一个事件时,跟踪将要采取的行动将变得更加困难.

您认为哪种方法更适合GUI建模.你知道其他可能对我的问题更好的陈述吗?

解决方法:

这是第三种选择:

>将状态机表示为转换矩阵

> Matrix列索引表示状态
>矩阵行索引表示符号(见下文)
>矩阵单元表示机器应该转移到的状态.这可能是新州或同一州
>每个州都有OnEvent方法,它返回一个符号

从StateMachine :: OnEvent(…)事件被转发到State :: OnEvent,它返回一个符号 – 执行的结果. StateMachine然后基于当前状态和返回的符号决定是否

>必须转换到不同的状态,或
>保持现状
>(可选)如果进行了转换,则会针对相应的状态调用OnExitState和OnEnterState

3个状态和3个符号的示例矩阵

0 1 2
1 2 0
2 0 1

在这个例子中,如果机器处于任何状态,状态(0,1,2)和State :: OnEvent返回符号0(矩阵中的第一行) – 它保持在相同的状态

第二行表示,如果当前状态为0并且返回符号为1,则转换为状态1.对于状态1 – >状态2和状态2 – >国家0.

类似的第三行表示对于符号2,状态0->状态2,状态1 – >状态0,状态2 – >州1

这点是:

>符号数量可能远低于州的符号数量.
>各国不了解对方
>所有转换都是从一个点进行控制的,所以当您想要以不同于NETWORK_ERROR的方式处理符号DB_ERROR时,您只需更改转换表并且不要触及状态实现.

标签:state-machine,c
来源: https://codeday.me/bug/20190901/1783565.html