极客秀
搜索

STM32F103也能部署神经网络?手把手实现NanoEdge模型在F103中运行!

前言

** 01. **

上期我们利用NanoEdge AI训练了一个异常检测的模型。

模型的最终大小被优化到了0.6KB的RAM以及1.9K的FLASH。如此精简的模型对于即便是只有64KBFlash的STM32F103C8T6也戳戳有余。

本期我们就利用STM32CubeIDE将这个模型嵌入到我们的工程中。步骤并不是很复杂我们一步一步来,先看看效果。

STM32CubeIDE配置

** 02. **


利用STM32CubeMX初始化工程,CubeMX中除了将工程选择为STM32CubeIDE之外没有其他需要更改的操作。

由于我是检测陀螺仪的异常数据,因此开启了一组I2C来与MPU6050.

除此之外由于核心板中并没有串口芯片,这里我开了USB实现虚拟串口进行通讯,大家使用的时候可以使用串口或者虚拟串口二选一来传输数据。

STM32CubeIDE为了资源的极致利用,默认在一些函数的浮点数运算方面需要单独配置的并且STM32CubeIDE默认是不进行代码优化的,这会导致我们的代码出现很多问题。因此我们需要对一些配置进行修改。


我们主要修改两个方面,第一是允许float类型即浮点类型可以在一些函数中使用以及开启编译器优化,主要优化的方面选择大小优化,防止内存空间溢出。

接着就导入我们训练好的库文件。

我们将压缩包中的NanoEdgeAI.h文件放入工程中的Inc头文件,也就是放置头文件的地方。

将libneai.a模型文件放在工程中找得到的地方。这里我选择放在了第一级界面(找得到就行)。


接着还是在刚才的配置界面,配置路径和标识符,选择库中,添加我们的库文件,这里只要填入文件名称就可以了。我们的文件名叫做:libneai.a
我们不需要前缀lib和后缀.a只需要填入neai即可。


接着就是添加模型所在的路径,可以选择绝对路径和工作区路径。这里我选择了工作区路径,找到.a文件所在的那一级目录选中即可。

这样子我们就完成了STM32CubeIDE的配置。

代码详解和使用

** 03. **

NanoEdgeAI.h文件中的内容非常简洁,主要有三个函数我们来仔细介绍一下。


enum neai_state neai_anomalydetection_init(void);enum neai_state neai_anomalydetection_learn(float data_input[]);enum neai_state neai_anomalydetection_detect(float data_input[], uint8_t *similarity);

三个函数的作用分别是:初始化,学习,预测。

初始化不必多说,在使用神经网络预测之前需要进行初始化,不需要任何参数。

学习函数是在使用前,需要至少一些组别数据进行训练,训练量由一个宏定义决定。

最后就是预测函数,由两个参数组成:输入变量和预测结果,预测结果使用一个uint8类型指针传入。最后得到0~100分的预测结果来判断数据是否正常。

所以整体i的API还是比较简单的。

需要注意的是,学习函数是第一次使用前必须调用的,但并不是一次性的。使用者的环境变化的话,并不一定代表着需要重新训练模型,可以重新利用学习函数让模型适应环境,关于这方面后续我也会了解更多,本期先介绍怎么使用。


float Data[3*128];unsigned char yuce;void fill_data(float * Data){  for(int j = 0;j<128;j++)  {    MPU6050_Read_All(&hi2c1, &MPU6050);    Data[j*3+0] = MPU6050.Ax;    Data[j*3+1] = MPU6050.Ay;    Data[j*3+2] = MPU6050.Az;    HAL_Delay(1);  }}

我们定义一组用以存放数据的Data数组,由于我们训练的模型是一个3轴传感器,并且每组1283个数据,因此定义一个3128的数组来存放传感器数据,定义函数来读取和填充。

接下来就是正式调用NanoEdgeAI的函数来实现功能啦。


  MPU6050_Init(&hi2c1);  neai_anomalydetection_init();  for(int i = 0;i<40;i++)  {    fill_data(Data);    neai_anomalydetection_learn(Data);  }

对MPU6050进行初始化,并且初始化NanoEdgeAI,进行40次的正常数据学习。


  fill_data(Data);  neai_anomalydetection_detect(Data,&yuce);  if(yuce<80)  {    HAL_GPIO_WritePin(GPIOC, GPIO_PIN_13, 1);  }  else  {    HAL_GPIO_WritePin(GPIOC, GPIO_PIN_13, 0);  }

在While循环中,持续获取MPU6050的数据,直接直接调用预测函数传入数据和结果变量。当预测结果小于80时,我们则认为检测到了异常让LED灯亮起来。

总结

** 04. **

总而言之,NanoEdge AI的使用较为简单和方便,在STM32F103C8T6等资源紧张的单片机中也可以实现模型部署。

虽然已经能看到有不少朋友会疑问:这不就是一个检测异常嘛?直接判断MPU6050的幅度不就好了。话是没错,但是事实上你知道MPU6050的幅度对应着数据异常这本身就是一种学习,只不过学习者是开发者还是单片机本身。

假如在复杂的环境下例如无人机陀螺仪,判断机翼是否出现异常。那么异常的变化在数据中体现的就不是一眼能看出来这么简单的事情了。而机器学习只需要将机翼异常的数据和正常情况下的数据建立模型即可判断。因此虽然本期Demo演示很简单,看似没什么大用,但是实际上却是以后实现检测中机器学习的起步。

当然NanoEdge还有好几个模型例如推理和多酚类模型,有机会也会出一些文章再仔细介绍介绍,大家有什么想要了解的,也可以私信和留言作者基本都会回复的。

1.转载请保留原文链接谢谢!
2.本站所有资源文章出自互联网收集整理,本站不参与制作,如果侵犯了您的合法权益,请联系本站我们会及时删除。
3.本站发布资源来源于互联网,可能存在水印或者引流等信息,请用户擦亮眼睛自行鉴别,做一个有主见和判断力的用户。
4.本站资源仅供研究、学习交流之用,若使用商业用途,请购买正版授权,否则产生的一切后果将由下载用户自行承担。
5.联系方式(#替换成@):pm#vimge.com

  相关内容