状态机表示

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

在阅读了这篇文章后,我发现了几种使用C ++建模状态机的方法,但我坚持使用2,但我不知道哪种方法更适合GUI建模。

  • 使用以下方法将状态机表示为状态列表:

  • OnEvent(...);
  • OnEnterState(...);
  • OnExitState(...);
  • StateMachine::OnEvent(...)我将该事件转发到CurrentState::OnEvent(...)并在这里做出是否做出转换的决定。 在转换时,我调用CurrentState::OnExitState(...)NewState::OnEnterState()CurrentState = NewState;

    通过这种方法,国家将与行动紧密结合,但是从一个国家我可以去多个国家并且我必须针对不同的转变采取不同的行动时, State可能会变得复杂。

  • 将状态机表示为具有以下属性的转换列表:

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

    通过这种方法, Transition将非常简单,但过渡次数可能会非常高。 另外,要追踪一个国家接收事件时将采取的行动将变得更加困难。

    你认为什么方法对GUI建模更好? 你知道其他表述可能对我的问题更好吗?


    这是第三个选项:

  • 将状态机表示为转换矩阵
  • 矩阵列索引表示一个状态
  • 矩阵行索引代表一个symbol (见下文)
  • 矩阵单元表示状态machihe应该转移到。 这可能既是新状态又是新状态
  • 每个状态都有一个返回symbol OnEvent方法
  • StateMachine::OnEvent(...)事件转发到State::OnEvent ,它返回一个symbol - 执行结果。 然后StateMachine基于当前状态并返回符号决定是否

  • 必须转换到不同的状态,或者
  • 当前状态被保留
  • 可选地,如果进行转换, OnExitState对应的状态调用OnExitStateOnEnterState
  • 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

    这是因为:

  • symbols数可能会比状态数低得多。
  • 各国不了解对方
  • 所有转换都是从一个点开始控制的,因此,当您想要将符号DB_ERRORNETWORK_ERROR不同地处理时,您只需更改转换表并且不要触摸状态实现。

  • 我不知道这是否是你期望的答案,但我用它直接处理这些状态机。

    使用枚举类型的状态变量(可能的状态)。 在GUI的每个事件处理程序中,测试状态值,例如使用switch语句。 做任何需要相应处理的事情,并设置下一个状态值。

    轻巧灵活。 保持代码的正常性使其可读性和“正式”。


    我个人更喜欢你说的第一种方法。 我发现第二个是非常直观和过于复杂的。 如果你在OnEnterState中设置了正确的事件处理程序,并在OnExitState中删除它们,你的代码将变得干净,并且所有的东西都将被自包含在相应的状态中,从而使读取变得简单。

    您还将避免使用巨大的开关语句来选择正确的事件处理程序或过程来进行调用,因为状态所做的每件事都可以在状态本身内完全可见,从而使状态机代码变得简短。

    最后但并非最不重要的一点,这种编码方式是从状态机绘制到你将使用的任何语言的精确翻译。

    链接地址: http://www.djcxy.com/p/53195.html

    上一篇: State machine representation

    下一篇: Python `with` context vs generators/coroutines/tasks