Pau*_*l R 17
对于简单的状态机,你可以在循环中使用switch语句,例如
for (;;)
{
switch (state)
{
case STATE_1:
// do stuff
// maybe change state
break;
case STATE_2:
// do stuff
// maybe change state
break;
case STATE_3:
// do stuff
// maybe change state
break;
// ...
}
}
Run Code Online (Sandbox Code Playgroud)
typedef std::pair<State,Message> StateMessagePair;
typedef std::map<StateMessagePair,State> StateDiagram;
StateDiagram sd;
// add logic to diagram
...
State currentState = getInitialState();
...
// process message
Message m = getMessage();
StateDiagram::iterator it=sd.find(std::make_pair(currentState,m)));
if (it==sd.end()) exit("incorrect message");
currentState = it->second;
Run Code Online (Sandbox Code Playgroud)
编辑: 建立状态图是这样完成的(例子是可乐自动售货机):
StateDiagram.insert(std::make_pair(State::Idle ,Message::MakeChoice ),State::WaitingForMoney);
StateDiagram.insert(std::make_pair(State::WaitingForMoney,Message::Cancel ),State::Idle);
StateDiagram.insert(std::make_pair(State::WaitingForMoney,Message::MoneyEntered ),State::FindCan);
StateDiagram.insert(std::make_pair(State::FindCan ,Message::CanSentToUser),State::Idle);
Run Code Online (Sandbox Code Playgroud)
可以使用第二个映射实现默认操作,其中键只是State,如下所示:
typedef std::map<State,State> StateDiagramForDefaults;
Run Code Online (Sandbox Code Playgroud)
逻辑可以在StateDiagramForDefaults中执行查找,而不是打印"不正确的消息".
如果需要将动作添加到状态图中,则映射的值应该是一个由动作和新状态组成的对,如下所示:
typedef std::pair<State,Message> StateMessagePair;
typedef std::pair<State,IAction *> StateActionPair;
typedef std::map<StateMessagePair,StateActionPair> StateDiagram;
Run Code Online (Sandbox Code Playgroud)
然后,构建图的逻辑应该"新"实现IAction的类的实例,并将其放在StateDiagram中.
然后,执行逻辑只通过虚拟方法(例如execute()或()-operator)执行IAction实现.
标准状态机实现技术是:
如果您不熟悉状态机并使用C或C++实现,我建议您阅读http://www.ddj.com/184401737上的 Dr.Dobbs文章"返回基础知识" (您需要点击打印链接)顶部方便阅读文本.)
所有标准技术都不适用于分层状态机(例如UML状态图).如果您对现代UML状态机感兴趣,我建议使用我的3部分Embedded.com文章"UML状态机中的速成课程"(http://www.embedded.com/design/testissue/215801043).
| 归档时间: |
|
| 查看次数: |
8358 次 |
| 最近记录: |