STM32状态机编程----什么是状态机?

article/2025/9/29 17:43:16

万事万物都有其状态

什么是状态

状态是人或事物表现出来的形态。是指现实(或虚拟)事物处于生成、生存、发展、消亡时期或各转化临界点时的形态或事物态势。

通过上面那句话,我们知道了状态就是一个对象在不同情况下对应的各种形态


做产品的时候,如果我们如果要对这个对象所有的形态进行描述,在一些对象复杂的逻辑状态下,比较复杂的逻辑问题,普通的流程图,或时序图对于对象和状态的解读缺乏直观的描述。

这个时候就需要状态机来对对象的各个形态进行描述,将对象的全部工作方式,分成几个场景,这些场景的工作方式不同,然后将这些场景通过数学模型表示出来


比方说一个小灯泡的开关,就是一个最基本的小型状态机
在这里插入图片描述
这里就是两个状态:①打开开关,灯泡亮,②关闭开关,灯泡灭

对应的状态机图:

在这里插入图片描述
这就是最简单的一个状态机

状态机方便的地方是,如果现在我们只有两种状态,这两个状态打开开关/关闭开关两个条件之间跳转,如果我们要加上一个新的条件,比方说我们设定了定时开关灯,多了一个跳转条件,如果灯泡开了超过8个小时就自动关闭,除非再次做打开开关,否则灯泡一致处于关闭状态,这个状态图如下:

在这里插入图片描述

是不是很方便

再举个最简单的例子。人有三个状态健康,感冒,康复中
触发的条件有淋雨(t1),吃药(t2),打针(t3),休息(t4)
所以状态机就是健康->(t4)->健康;健康->(t1)->感冒;感冒->(t3)->健康;感冒->(t2)->康复中;康复中->(t4)->健康,等等。就是这样状态在不同的条件下跳转到自己或不同状态的情况,就叫做状态机。

状态机要素

通过上面的举例,我们可以讲状态机可归纳为4个要素,即现态、条件、动作、次态。这样的归纳,主要是出于对状态机的内在因果关系的考虑。“现态”和“条件”是因,“动作”和“次态”是果。详解如下:

  • 现态:是指当前所处的状态。

  • 条件:又称为“事件”,当一个条件被满足,将会触发一个动作,或者执行一次状态的迁移。

  • 动作:条件满足后执行的动作。动作执行完毕后,可以迁移到新的状态,也可以仍旧保持原状态。动作不是必需的,当条件满足后,也可以不执行任何动作,直接迁移到新状态。

  • 次态:条件满足后要迁往的新状态。“次态”是相对于“现态”而言的,“次态”一旦被激活,就转变成新的“现态”了。

状态机是一种编程思路。是现实事物运行规则抽象而成的一个数学模型。

有限状态机

有限状态机简称就是状态机,因为一般的状态机的状态都是离散和可举的,即为有限,所以后面的介绍都不加有限二字**。状态机表示有限个状态以及在这些状态之间的转移和动作等行为的数学模型**。通俗的描述状态机就是定义了一套状态変更的流程:

状态机包含一个状态集合,定义当状态机处于某一个状态的时候它所能接收的事件以及可执行的行为,执行完成后,状态机所处的状态。

状态迁移图(STD)

在这里插入图片描述

  • (1)状态框:用方框表示状态,包括所谓的“现态”和“次态”;
  • (2)条件及迁移箭头:用箭头表示状态迁移的方向,并在该箭头上标注触发条件;
  • (3)节点圆圈:当多个箭头指向一个状态时,可以用节点符号(小圆圈)连接汇总;
  • (4)动作框:用椭圆框表示;
  • (5)附加条件判断框:用六角菱形框表示;

状态表:
在这里插入图片描述

STM32中的状态机

举个简单的例子:就按键处理来说,按键动作本身也可以看做一个状态机。一个细小的击键动作包含了:释放、抖动、按下、抖动和重新释放等状态。  当我们打开思路,把状态机作为一种思想导入到程序中去时,就会找到处理疑问的一条有效的捷径。有时候用状态机的思维去思考程序该干什么,比用控制流程的思维去思考,可能会更有效。这样一来状态机便有了更实际的功用。废话不多说,实践才是检验真理的唯一标准。

也许有人觉得状态机把问题复杂化了,其实我们在编写代码的时候在无形之中已经使用了状态机的思想,比方说我们的if else 判断

if else语句结构状态机

if 条件1else if  条件2else if   条件3...else  条件n

我们知道C语言的if else if语句是从第一条开始判断的,如果符合条件的那一行永远在后面几行,那么就要每次多执行很多次的if …而if是判断语句,括号内的判断是要执行运算的,即使是单周期指令的MCU,在进行乘除运算等都需要消耗多个时钟周期,因此,每次多执行1次判断至少浪费一个时钟周期甚至更多,因此,这样子的状态机无疑是效率低下的,系统软件设计会很复杂。

switch case结构状态机

 switch()。case1:if(not反复执行状态1)。进入1状态前要做的准备。进入1状态的过程。if(not反复执行状态1)。离开状态1的过程。case2:...

使用Switch case 相较于if else的好处就是可以清楚的看到所有的状态,然后代码架构更清楚点,但是实际的运行效率还是没有提高


再说一下使用Switch编写状态机的两种写法

我们假设状态机的状态转换由下表所示:在这里插入图片描述当处于State0时发生event0 则执行action0并将状态变成state1,当state1状态下发生event2则执行action6并将状态变成state2。以此类推。

下面描述下实现上述状态机的两种不同的写法:
1)竖着写:在状态中判断事件,并执行相应的操作,完成相应的状态转换。
2)横着写:在事件中根据当前的状态,执行相应的操作,完成相应的状态转换。

//竖着写
switch(cur_state)
{case State0:if(event1){action0;cur_state = State1;}else if(event2){action4;cur_state = State1;}else if(event3){action5;cur_state = State2;}break;case State1:if(event1){action1;cur_state = State2;}else if(event3){action6;cur_state = State0;}break;case State2:if(event1){action3;cur_state = State0;}break;default:break;
}
//横着写
void event0func(void)
{switch(cur_state){case State0:action0;cur_state = State1;break;case State1:action1;cur_state = State2;break;case State2:action1;cur_state = State0;break;default:break;}
}void event1func(void)
{switch(cur_state){case State0:action4;cur_state = State1;break;default:break;}
}void event2func(void)
{switch(cur_state){case State0:action5;cur_state = State2;break;case State1:action6;cur_state = State0;break;default:break;}
}

上述两种写法实现的功能完全相同,对比两种写法:

1)写法1(竖着写)使用了if -else if语句隐含了优先级,破坏可事件间的原有关系(各个时间应该同优先级)
2)写法1(竖着写)在结构上是顺序查询方式(查询事件),浪费大量的时间,而且时间不可估算。
写法2(横着写)因为在某个时间点上状态是唯一确定的,在时间处理函数中通过switch语句可直接定位到相同状态,执行时间也可以估算。
3)写法2(横着写)比较直观,程序执行效率较高。
总体来说:写法2要优于写法1。

但是不论是在事件中判断状态,在状态中判断事件,横竖两种写法的代码都比较冗长,看起来呢也不大好,一旦增减,就又要动脑子重新梳理一遍,实际编写我们并不采用这两种写法


那么下一节我们将用STM32实现LED的状态机编程,用状态机的4个要素,让您了解下状态机编程的方便之处。

请添加图片描述

请添加图片描述


http://chatgpt.dhexx.cn/article/L94mrBGB.shtml

相关文章

什么是状态机?一篇文章就够了

1 概述 状态机[1]一般指有限状态机(英语:finite-state machine,缩写:FSM)又称有限状态自动机(英语:finite-state automaton,缩写:FSA),是表示有限…

C语言_有限状态机(FSM)

C语言_有限状态机(Finite State Machine) 基本介绍 许多小型或复杂的应用程序都使用有限状态机 (FSM),C 语言中的有限状态机是嵌入式系统的流行设计模式之一,有限状态机使开发变得容易和顺利。 有很多设备使用事件基态&#xf…

Unity字体展示下载

Unity字体种类展示 这是字体包里面的图片,是不是很多种字体. 下载链接: https://download.csdn.net/download/qq_42603590/12001130 这是下载字体包的地方,很便宜.没有积分的可以留言,我发给你 有时候可能回复的不是很快(抱拳了) 喜欢的话点个赞,关注一下再走吧,谢谢

Unity 之 官网下载地址,方便各个版本的 Unity 安装包下载

Unity 之 官网下载地址,方便各个版本的 Unity 安装包下载 目录 Unity 之 官网下载地址,方便各个版本的 Unity 安装包下载 一、简单介绍 二、各个版本下载入口网址 一、简单介绍 在 Unity 的下载地址现在不是很好找,这里保存一下 Unity 各…

Unity入门之路0-Unity下载安装以及版本选择

文章目录 下载链接Unity Hub和Unity的关系UnityHub下载(Win)两者比较 Unity版本选择许可证问题 下载链接 一定不要百度或者去垃圾网站下载盗版网站 ,Unity是正版免费的,官方很关注使用者的感受,所以下载官网的就没问题。 https://unity.cn/re…

UnityHub下载缓存位置

一、下载Unity各版本的编辑器 C:\Users\XXX\AppData\Local\Temp\unityhub-xxx-xxx-xxx-xxx 我电脑是 C:\Users\Administrator\AppData\Local\Temp\unityhub-xxxx-xxxx 如果你不需要备份安装包,那么这个缓存的文件夹,就与你无关了,因为安装完…

使用UnityHub下载任意版本Unity

目录 方法一 使用链接方法二 官网下载(适用于2018.4.23及以上版本) unityHub上只能下载官方指定的版本,很多其他版本不能下载,下面介绍的是在unityHub下载任意版本的方法 方法一 使用链接 举例: 2019.2.11f1版本的unity----> unityhub://2019.2.11f1/5f859a4cfee5 格式 unit…

Unity给游戏对象贴图、从官网下载资源、导入导出

1、新建项目、在项目场景中创建几何对象并修改参数 在层级“”中创建一个立方体(3D对象),同理也创建一个球体 创建好的立方体会显示在场景视图中 (从场景视图或层级视图中)选中几何体,选择场景视图中竖排工…

unity下载网页所有图片

用unity的c#脚本批量下载网页上的所有图片 1、将网页的html保存到本地 在网页上鼠标右击另存为如下图所示 保存html文件 2、通过截取<img“”>获取图片存储的地址 经过两个步骤之后就可以开始着手敲代码了 代码 html下载的本地地址和要保存的图片地址 //保存在本地ht…

Unity下载方法(超详细)

一、进入官网&#xff0c;点击[下载Unity]&#xff0c;点击右上角的小人头像&#xff0c;点击[创建Unity ID](创建ID的方法你点进去按照它要求你的一步一步做就行啦)。 二、创建完Unity ID并登录(或已有Unity ID并登录)后&#xff0c;下拉网页&#xff0c;点击[下载Unity Hub]&…

Unity 改变下载资源商店中资源默认路径的方法

Unity 改变下载资源商店中资源默认路径的方法 Unity资源商店中免费资源可以被我们很好的使用&#xff0c;尤其对于暂时还不会自己设计资源的创作者。但是&#xff0c;unity默认是将资源商店的下载路径设置在了C:\Users\操作系统当前用户\AppData\Roaming\Unity\Asset Store-5.x…

Unity 各版本下载方法

开发Unity的&#xff0c;获取不同版本Unity版本和了解Unity最新动态很重要&#xff0c;现在更新迭代很频繁&#xff0c;在开发时&#xff0c;不论遇到项目升级&#xff0c;还是插件要求&#xff0c;还是老项目运行&#xff0c;总是在多个版本间切换。 是不是经常遇到&#xff0…

Unity3d_NGUI和UGUI的学习

由于之前刚入门的时候&#xff0c;应Unity3d整体发展的要求我们自学了UGUI(相对来说UGUI比NGUI做得更好一些&#xff0c;后面会有2者对比)&#xff0c;但是后来公司要求使用NGUI&#xff0c;所以我这边把之前学习UGUI&#xff08;不全&#xff0c;当时资源有限&#xff09;和NG…

NGUI与UGUI的区别及其优缺点

UIGUI与BGUI 的区别 首先说一下NGUI NGUI是严格遵循KISS原则并用C#编写的Unity&#xff08;适用于专业版和免费版&#xff09;插件&#xff0c;提供强大的UI系统和事件通知框架。其代码简洁&#xff0c;多数类少于200行代码。这意味着程序员可以很容易地扩展NGUI的功能或调节已…

NGUI的使用教程与实例

原文地址&#xff1a;http://www.tasharen.com/?page_id185 NGUI下载地址&#xff1a;点我传送 NGUI教程&#xff1a;步骤1-Scene 1.创建一个新的场景&#xff08;New Scene&#xff09;。 2.选择并删除场景里的MainCamera。 3.在NGUI菜单下选择Create a New UI&#xff0c…

Unity NGUI 插件 简介

文章目录 Unity NGUI一. NGUI基础1.1 导入NGUI插件1.2 基本UI资源1.3 制作UI图集1.4 制作UI字体1.5 UIRoot、UIPanel 和 UICamera 组件1.6 Depth (深度) 二. 核心组件2.1 UISprite (精灵)2.2 UILabel (标签)2.3 UITexture (纹理)2.4 UIButton (按钮)2.5 UISlider (进度条)2.6 U…

Unity3D种UGUI与NGUI的对比差别(2)

层级管理概念UGUI采用Hierarchy排序的方式&#xff0c;替代了NGUI中的Depth排序。更精准的说&#xff0c;NGUI的排序是通过Depth、Z值、RenderQueue共同影响的&#xff0c;整体规则过于复杂&#xff1b;而UGUI采用的排序比较简单&#xff0c;在Canvas内部元素采用Hierarchy方式…

NGUI插件] 收录最全的NGUI示例文档中文教程(更新版本3.0.5)

NGUI3.0.X官网示例中文讲解 本站NGUI各个版本插件下载地址 NGUI 2.7.0中文字体的使用 官方网站上的控件说明翻译: NGUI控件说明(中文) UIWidget NGUI控件说明(中文) UIRoot NGUI控件说明(中文) UIPanel NGUI控件说明(中文) UICamera NGUI控件说明(中文) UIStretch NGUI控件…

NGUI 3.5教程(一)安装NGUI 3.5.8

写在前面&#xff1a; 网上找的NGUI教程&#xff0c;都是基于2.x版本的。为了能配合教程学着做&#xff0c;我也是下载了各种NGUI 2.x版本。但是在导入的时候&#xff0c;或多或少都报错&#xff08;我用的Unity 的版本是4.3.2&#xff09;。无奈之下&#xff0c;只好下载了最…

[Unity3D]事半功倍:界面插件NGUI的使用教程与实例

原文地址&#xff1a;http://www.tasharen.com/?page_id185 NGUI下载地址&#xff1a;点我传送 NGUI教程&#xff1a;步骤1-Scene 1.创建一个新的场景&#xff08;New Scene&#xff09;。 2.选择并删除场景里的MainCamera。 3.在NGUI菜单下选择Create a New UI&#xff0c…