Boost StateChart实现状态机----秒表例程
Boost 提供了状态机的实现接口,采用了CRTP技术实现,下面以秒表为例子实现一个状态机,这是一个官方的例子,也可以参考资料:Boost Statechart 庫,状态机的状态转换图如下所示:

实现代码如下:
#include <stdio.h>
#include <stdlib.h> #include <iostream> // std::cout
#include <thread> // std::thread
#include <string>
#include <vector>
#include <ros/ros.h>
#include <boost/statechart/state_machine.hpp>
#include <boost/statechart/state.hpp>
#include <boost/statechart/event.hpp>
#include <boost/statechart/transition.hpp>
#include <boost/statechart/custom_reaction.hpp>
#include <boost/range/irange.hpp>
#include <boost/thread/thread.hpp> #include <ctime> using namespace std;
namespace sc = boost::statechart; class EvStartStop : public sc::event<EvStartStop>
{
};
class EvReset : public sc::event<EvReset>
{
}; /*虚类,用于状态机获取状态*/
class IElapsedTime
{
public:
virtual double elapsedTime() const = ;
virtual ~IElapsedTime(){};
}; class Active;
/*秒表,状态机*/
class StopWatch : public sc::state_machine<StopWatch, Active>
{
public:
double elapsedTime() const
{
return state_cast<const IElapsedTime &>().elapsedTime();
}
}; class Stopped;
/*活动状态*/
class Active : public IElapsedTime, public sc::state<Active, StopWatch, Stopped>
{
public:
typedef sc::transition<EvReset, Active> reactions; Active(my_context ctx)
: my_base(ctx),
elapsed_time_()
{
cout << "Entry Active" << endl;
}
~Active()
{
cout << "Exit Active" << endl;
} double elapsedTime() const
{
return elapsed_time_;
}
double& elapsedTime()
{
return elapsed_time_;
} private:
double elapsed_time_;
}; /*计时状态*/
class Running : public IElapsedTime, public sc::state<Running, Active>
{
public:
typedef sc::transition<EvStartStop, Stopped> reactions;
Running(my_context ctx)
: my_base(ctx),
start_time_(std::time())
{
cout << "Entry Running" << endl;
}
~Running()
{
context<Active>().elapsedTime() = elapsedTime();
cout << "Exit Running" << endl;
}
virtual double elapsedTime() const
{
return context<Active>().elapsedTime()
+ std::difftime(std::time(), start_time_);
}
private:
std::time_t start_time_;
}; /*停止状态*/
class Stopped : public IElapsedTime, public sc::state<Stopped, Active>
{
public:
typedef sc::transition<EvStartStop, Running> reactions;
Stopped(my_context ctx)
: my_base(ctx)
{
cout << "Entry Stopped" << endl;
}
~Stopped()
{
cout << "Exit Stopped" << endl;
}
virtual double elapsedTime() const
{
return context<Active>().elapsedTime();
} }; int main(int argc, char** argv)
{
StopWatch myWatch;
myWatch.initiate();
cout << "---" << endl; myWatch.process_event(EvStartStop());
for(int i = ; i < ; i++)
{
boost::this_thread::sleep(boost::posix_time::seconds()); //休眠1秒
std::cout << "time:" << myWatch.elapsedTime() << "\n";
}
myWatch.process_event(EvStartStop());
boost::this_thread::sleep(boost::posix_time::seconds());
std::cout << "current time:" << myWatch.elapsedTime() << "\n";
cout << "---" << endl;
myWatch.process_event(EvReset());
std::cout << "reset time:" << myWatch.elapsedTime() << "\n";
cout << "---" << endl;
return ;
}
运行效果如下:
Entry Active
Entry Stopped
---
Exit Stopped
Entry Running
time:
time:
time:
time:
time:
time:
time:
time:
time:
time:
Exit Running
Entry Stopped
current time:
---
Exit Stopped
Exit Active
Entry Active
Entry Stopped
reset time:
---
Exit Stopped
Exit Active
Boost StateChart实现状态机----秒表例程的更多相关文章
- c# 状态机实现
c#仿boost statechart的状态机.去年转到unity使用c#,statechart原来的风格蛮爽的,缺点是编译忒慢,在c#则编译根本不是问题. 不一样的地方首先是简单!因为没做一些东西如 ...
- boost状态机学习二(秒表)
基础主题:秒表 下面我们要为一个机械秒表建模一个状态机.这样一个秒表通常会有两个按钮. * Start/Stop * Reset 同时有两种状态: * Stoped: 表针停留在上次停止时的位置: o ...
- Boost的状态机库教程(1)
介绍 Boost状态机库一个应用程序框架,你可以用它将UML状态图快速的转换为可执行的c++代码,而不需要任何的代码生成器.它支持几乎所有的UML特征,可以直接了当的转换,并且转换后的c++代码就像对 ...
- Boost 1.61.0 Library Documentation
http://www.boost.org/doc/libs/1_61_0/ Boost 1.61.0 Library Documentation Accumulators Framework for ...
- Ceph源码解析:PG peering
集群中的设备异常(异常OSD的添加删除操作),会导致PG的各个副本间出现数据的不一致现象,这时就需要进行数据的恢复,让所有的副本都达到一致的状态. 一.OSD的故障和处理办法: 1. OSD的故障种类 ...
- Ceph:pg peering过程分析
转自:https://www.ustack.com/blog/ceph%ef%bc%8dpg-peering/ Peering:互为副本的三个(此处为设置的副本个数,通常设置为3)pg的元数据达到一致 ...
- 【资料下载区】【iCore3相关代码、资料下载地址】更新日期2017/1/5
[iCore3 ARM代码下载地址][全部]DEMO1.0测试程序发布例程一:ARM驱动三色LED例程二:读取arm按键状态例程三:EXTI中断输入实验——读取ARM按键状态例程四:USART通信实验 ...
- Important Programming Concepts (Even on Embedded Systems) Part V: State Machines
Earlier articles in this series: Part I: Idempotence Part II: Immutability Part III: Volatility Part ...
- 记录一次ceph recovery经历
一次ceph recovery经历 背景 这是一个測试环境. 该环境中是cephfs 一共12个节点, 2个client.2个mds.8个osd mds: 2颗CPU,每一个4核.一共是8核. 128 ...
随机推荐
- Guava HashMultiMap(MultiMap)反转映射
(一)MultiMap 多重map,一个key可以对应多个值(多个值放在一个list中),可用于分组 举例: Multimap<String, Integer> map = HashMul ...
- Linux 网络操作
Linux 基础网路操作 ifconfig eth0 down # 禁用网卡 ifconfig eth0 up # 启用网卡 ifup eth0: # 启用网卡 mii-tool em1 # 查看网 ...
- Ajax和jsonp区别
大多数情况下,无论是框架还是自己实现都是通过Ajax的方式来向后端请求数据的,而Ajax之间是通过传输json格式的文件来进行数据的传输的,大家对Ajax也很熟悉了,那么为什么我又要使用jsonp呢? ...
- [HAOI2008]移动玩具(状压&带权二分图)
题目描述 • 一个 4 × 4 的 0/1 矩阵 • 每次可以交换相邻两个元素 • 求从初始状态到目标状态的最小交换次数 输入格式 前四行,每行一个长为 4 的 0/1 字符串,描述初始状态. 后四行 ...
- Javascript - Vue - vue对象的生命周期
vue对象的生命周期 从vue的创建到销毁会经过一系列的事件,这是vue对象的生命周期. 创建期间的生命周期函数 <div id="box"> <h3 id ...
- Python学习一|anaconda的安装问题以及Python语言的特点
安装时遇到的问题 安装anaconda3.0到D盘之后,配置好两个环境变量:D:\anaconda和D:\anaconda\Scripts.发现在命令行中执行python指令可以,但conda指令却是 ...
- Coursera台大机器学习技法课程笔记08-Adaptive Boosting
将分类器组合的过程中,将重点逐渐聚焦于那些被错分的样本点,这种做法背后的数学原因,就是这讲的内容. 在用bootstraping生成g的过程中,由于抽样对不同的g就生成了不同的u,接下来就是不断的调整 ...
- python标准模块(下)
Python 系统标准模块(shutil.logging.shelve.configparser.subprocess.xml.yaml.自定义模块) 目录: shutil logging模块 she ...
- SendMessage原理初探
今天跟踪一下SendMessage的实现. 用向导先创建一个Windows application. 向导生成了一个简单的窗口,如下. 在File菜单添加SendMessage,顺便添加一个PostM ...
- MediatR 中介模式
使用MediatR完成基于内存级别的消息发布订阅 在微服务架构中领域驱动模型中处理领域事件的相关操作 在区分好领域模型后,就拿代码中来说嘛,用户领域中添加用户操作可能或存在跟用户相关的一些领域事件,在 ...