写点什么

一个有限状态机的 C++ 实现

  • 2019-11-20
  • 本文字数:1264 字

    阅读完需:约 4 分钟

一个有限状态机的C++实现

有限状态机:表示有限个状态以及在这些状态之间的转移和动作等行为的数学模型。它对数字系统的设计具有十分重要的作用。常见的计算机就是使用有限状态机作为计算模型的;电脑游戏设计中也经常使用有限状态机模型。本文就讲讲一个状态机的 C++实现。

有限状态机

什么是有限状态机?

简单说就是作一件事可能会经过多个不同状态的转换, 转换依赖于在不同时间发生的不同事件来触发, 举个例子,比如 TCP 的状态转换图, 在实现上就可以用 FSM.


传统的实现方案

if…else : 搞一大堆 if else, 一个函数写很长很长…


swich…case : 也搞一大堆一个函数写很长很长…

FSM 的实现方案

根据具体的业务需要, 将业务的处理流程定义为一个状态机, 此状态机中存在以下必要元素


1.根据业务需要, 拆解抽象出若干个不同状态 State, 并确定此状态机的初始状态;


2 根据实现需要, 抽象出用于触发状态转换的事件 Event;


3.为了处理一个 Event, 需要定义状态的转换过程 Transition;


4.状态机要先判断当前所处的状态是否与当前发生的 Event 匹配(注意: 相同的状态可能同时匹配多个 Event)。


用张简图来说明一下



1.MachineSet 可以同时管理多个 Machine;


2.外部触发的 Event 进入到 MachineSet 的事件队列;


3.事件队列里的 Event 被顺序处理, 被 Dispatch 到 match 的 Machine;


4.Machine 根据当前的所处的 state 和 Event 类型来判断当前 Event 是否有效;


5.如果上面(4)中的 Event 有效, 则进行状态转换;


6.状态转换具体来说涉及到三个回调函数:


6.1 当前 state 离开, 是第一个回调,需要使用者根据实际需要处理;


6.2 trasition 这个转换过程, 是第二个回调;


6.3 新 state 的进入, 是第三个回调;


一个简单的状态机,差不多就是上面这些内容, 剩下的就是用程序语言把它实现出来了;

FSM 的 C++ 实现

一个用 C++11 实现的 FSM 的代码


https://github.com/DavidLiuXh/kuafu
复制代码


实现简介:


主要就是按 deamo 里的思路, 封装了以下几个模块


MachineSet,


Machine,


Event,


Transition,


Predicate


对于 Event 的处理, 提供两种方案:


1.直接使用 MachineSet 提供的 StartBackground, 开启一个 work thread, 在这个 work thread 中不断从存储 event 的 fifo 队列中获取 event 后 dispatch 到各个 machine;


2.不使用 MachineSet 提供的 event fifo, 实现自己的 MachineSetHandler, 将其实例注册到 MachineSet, 从 event 的派发;

一个具体的实现

我们来使用上面的 FSM 的实现来模拟一个用户登陆的场景;


定义用到的 Event 和几种不同的事件类型



定义用到的状态机, 从 kuafu::StateMachine 继承, 其中包括用过的几种 state 和 transition



在 Birth()函数中构造 state 和 transition, Birth()是 StateMachine 的一个虚函数, 每个用户实现的 Machine 都需要实现它:



创建 MachineSet, 并开始 event 处理线程



创建用户定义的 Machine, 设置初始状态



设置 state 和 transition 相应的回调



模拟 event 发生:



相关源码:



本文转载自公众号 360 云计算(ID:hulktalk)。


原文链接:


https://mp.weixin.qq.com/s/BVaOWSzUsGldbmQk9QZgFw


2019-11-20 15:174178

评论

发布
暂无评论
发现更多内容

Vue&SpringBoot前后端项目分离构建

夏悸

Spring Boot Vue 大前端

ChaosBlade:从零开始的混沌工程(一)

郭旭东

云原生 混沌工程

自学技术看这些网站就够了!

我是程序员小贱

学习

CDN百科第三讲 | 如果用了云服务器,还需要做CDN加速吗?

阿里云Edge Plus

CDN

分布式场景之刚性事务-2PC详解

奈学教育

分布式 2PC

装饰模式——看JDK和Spring是如何杜绝继承滥用的

大头星

Java spring jdk 面试 设计模式

ARTS - Week 2

Khirye

ARTS 打卡计划 arts

别再说你不懂Linux内存管理了,10张图给你安排的明明白白

程序员柠檬

Linux 后台开发

分布式事务 - 分布式事务框架Seata

Java收录阁

分布式事务

有时候爱也是一种负担

小天同学

日常思考 爱情 个人感悟

观察者模式——窥探JDK和Spring中的设计模式

大头星

spring jdk 面试 设计模式 Java 25 周年

人人都能看懂的 6 种限流实现方案!(纯干货)

王磊

Java 「Java 25周年」 Java 25 周年

RUST IN BLOCKCHAIN 五月简报

Aimee 阿敏

rust crypto blockchain

原创 | TDD工具集:JUnit、AssertJ和Mockito (十八)编写测试-测试执行顺序\嵌套的测试

编程道与术

Java 编程 TDD 单元测试 JUnit

绝对坦诚:打造团队自我进化能力的最佳姿势

伴鱼技术团队

团队管理 企业文化 团队协作 技术管理 文化

9种 分布式ID生成方案,我替你整理好了

程序员小富

Java MySQL 分布式

地摊经济一千年:从《韩熙载夜宴图》到木屋烧烤“撸串”

punkboy

产品经理 商业 新闻动态 新基建 地摊

2020.06.04,我在《架构师训练营》的学习历程:架构方法

程序员二师兄

极客大学架构师训练营

使用Nginx防止IP地址被恶意解析

Noneplus

nginx 恶意解析

重学 Java 设计模式:实战桥接模式(多支付渠道「微信、支付宝」与多支付模式「刷脸、指纹」场景)

小傅哥

设计模式 小傅哥 重构 代码质量 桥接模式

【写作群星榜】5.29~6.4写作平台优秀作者&文章排名

InfoQ写作社区官方

写作平台 排行榜 热门活动

我的编程之路 -7(T型人才)

顿晓

T型人才 编程之路

白话说流——什么是流,从批认识流(一)

KAMI

大数据 flink 流计算

极客大学架构师训练营 听课总结 -- 第一课

John(易筋)

极客时间 架构 极客大学 架构师 极客大学架构师训练营

不同层次格局的差异

kimmking

如果我能找到工作,那么你也行

escray

架构师训练营-第一节

Geek_af3d01

六处提及区块链!海南自贸港区块链产业应用先行,与“币”划清界限

CECBC

区块链技术 海南方案 严控 产业

不到100行代码的iOS组件化你怕了么?

Geek_i59t1w

ios 组件化 url scheme scheme

ARTS-week1

书生

初识软件架构

陈皮

Architecture Architect

一个有限状态机的C++实现_文化 & 方法_刘伟_InfoQ精选文章