一个简单的有限状态机如图所示:
状态机几个要素: 状态state、事件event、动作action。这个状态机有两个状态,State1状态,和结束状态, 在Event1发生时会触发action(或者默认没有action),从而状态发生迁移。
boost的状态机库(Boost.MetaStateMachine )分为 back-end 和 front-end; 根据 front-end 的不同有三种实现,而 back-end 只有一种实现。
basic front-end
function front-end
eUML front-end
basic front-end 和 funciton front-end 都是通过创建类,继承类,定义成员变量来实现; 而 eUML front-end 是通过重用UML状态机,利用一些c++宏来实现的,感觉比较代码清晰简洁(见链接)
下列代码利用 function front-end 来实现上述状态机:
#include
#include
#include
#include
namespace {
namespace msm = boost::msm;
namespace msmf = boost::msm::front;
namespace mpl = boost::mpl;
// ----- Events
struct Event1 {};
// ----- State machine
struct Sm1_:msmf::state_machine_def
{
// States
struct State1:msmf::state<>
{
// Entry action
template
void on_entry(Event const&, Fsm&) const {
std::cout << "State1::on_entry()" << std::endl;
}
// Exit action
template
void on_exit(Event const&, Fsm&) const {
std::cout << "State1::on_exit()" << std::endl;
}
};
struct End:msmf::terminate_state<> {};
// Set initial state
typedef State1 initial_state;
// Transition table
struct transition_table:mpl::vector< // Start Event Next Action Guard msmf::Row < State1, Event1, End, msmf::none, msmf::none >
> {};
};
// Pick a back-end
typedef msm::back::state_machine Sm1;
void test()
{
Sm1 sm1;
sm1.start();
std::cout << "> Send Event1" << std::endl;
sm1.process_event(Event1());
}
}
int main()
{
test();
return 0;
}
// Output:
//
// State1::on_entry()
// > Send Event1
// State1::on_exit()
Sm1_ 对象表示这个状态机. 在 Sm1_状态机中有两个state,分别为:State1和End. 初始伪状态通过如下语句定义:
// Set initial state
typedef State1 initial_state;
typedef xxx initial_state 表示状态机Sm1_从状态State1开始。
利用 eUML 实现一个灯泡的状态机(state:on,off; action: press)
#include
#include
#include
#include
namespace msm = boost::msm;
using namespace boost::msm::front::euml;
BOOST_MSM_EUML_STATE((), Off)
BOOST_MSM_EUML_STATE((), On)
BOOST_MSM_EUML_EVENT(press)
BOOST_MSM_EUML_TRANSITION_TABLE((
Off + press == On,
On + press == Off
), light_transition_table)
BOOST_MSM_EUML_DECLARE_STATE_MACHINE(
(light_transition_table, init_ << Off),
light_state_machine)
int main()
{
msm::back::state_machine light;
light.process_event(press);
light.process_event(press);
}
// 代码稍微少一点哈~