演讲主题是对比状态机各种实现上的效率,源代码2,项目文档1,ppt3见参考链接


简单说,SML在各种benchmark比较上没拖后腿,然后列举了各种实现上的优缺点

具体的比较图标还是看ppt3吧,一张一张截图太费劲了,这里主要把各种实现的优缺点列一下,所有代码实现见参考链接4

if/else状态机

  • (+) 内联
  • (+) 没有堆内存分配
  • (~) 内存占用小
  • (-) 不可复用 if-else hell

switch/enum状态机

  • (+) 内联
  • (+) 没有堆内存分配
  • (~) 内存占用小
  • (-) 不可复用

继承 状态模式

  • (+) 容易复用,扩展(重写接口即可)
  • (~) 内存占用稍高
  • (-) 堆内存分配
  • (-) 无法内联,效率不行

std::variant + std::visit

  • (+) 内存占用低,高效
  • (+) 集成了std::expected
  • (~) 内联 (clang)
  • (-) 无法复用,类似switch/enum,类型加强了

coroutines + loop

  • (+) c++ 特性,组织好
  • (+) 很容易切换成同步异步的版本
  • (~) 学习曲线高,和上面的思路不同
  • (~) 堆内存 (heap elision / devirtualization)
  • (~) 隐式状态(需要提供函数默认行为)
  • (-) 所有事件都是相同的类型
  • (-) 奇怪的死循环写法

coroutines + goto

  • (+) 没有死循环
  • (+) 显式状态
  • (-) goto

coroutines + functions + variant

把死循环放到函数里,co_return 函数

  • (+) 容易维护,添加新事件状态
  • (+) 类型安全事件

boost statechart

  • (+) UML
  • (~) 学习曲线高,类似状态模式,写接口
  • (-) 动态类型
  • (-) 动态派发
  • (-) 高内存使用

boost msm

  • (+) UML 声明模式
  • (+) 分派实现,jump table
  • (+) 内存使用很小
  • (~) 学习曲线高
  • (~) DSL
  • (-) 宏
  • (-) 编译时间漫长
  • (-) 错误信息恐怖

boost sml

现代,可指定多种分派策略 jump table / nested switch / fold expressions

  • (+) UML 声明模式

  • (+) 编译期定制

  • (+) 内联,O1分派

  • (+) 编译速度快

  • (+) 占用内存小

  • (~) DSL

  • (~) 学习曲线高

reference

  1. https://boost-experimental.github.io/sml/
  2. https://github.com/boost-experimental/sml
  3. 演讲ppt
    1. 在线https://boost-experimental.github.io/sml/cppcon-2018/#/
    2. pdfhttps://github.com/CppCon/CppCon2018/tree/master/Presentations/state_machines_battlefield_naive_vs_stl_vs_boost
  4. ppt中的demo实现 https://github.com/boost-experimental/sml/tree/master/benchmark/connection

或者到博客上提issue 我能收到邮件提醒。