PID算法在电机速度控制上的应用
目录
概述
1 系统硬件框架
1.1 框架介绍
1.2 硬件实物图
2 STM32Cub生成工程
2.1 软件版本信息
2.2 配置参数
编辑2.3 生成项目
3 PID算法实现
3.1 概念
3.2 代码实现
4 其他功能实现
4.1 设置电机速度
4.2 PID算法控制电机
4.3 功能函数的调用
5 测试
5.1 测试案例1
5.2 测试案例2
源代码下载地址:
PID算法在电机速度控制上的应-测试源码资源-CSDN文库
概述
本文主要介绍使用PID算法实现电机速度的控制,笔者使用IO外部中断测试码盘的脉冲实现测速功能,通过该速度值,应用PID算法实现调制PWM的占空比,以实现电机速度的控制。
1 系统硬件框架
1.1 框架介绍
1) 系统使用光电编码器进行速度测试,具体实现方式可以参看原文:
电机转速计算(基于码盘和IO外部中断)-CSDN博客
2) TIMER7实现定时器功能,其会产生10us的定时器中断,为系统工作提供基准时钟。
3)TIMER8用于产生PWM实现电机速度控制,系统通过电机速度的反馈值以调节PWM的脉冲宽度,以实现电机速度的闭环控制。

1.2 硬件实物图
使用STM32F103RC作为主控芯片,LN298N用于驱动电机,光电码盘用于测试电机转速。具体的测试实物图如下:
2 STM32Cub生成工程
2.1 软件版本信息
| 软件名称 | 版本信息 |
|---|---|
| STM32Cube | STM32CubeMX 6.11 |
| STM32 HAL | STM32Cube_FW_F1_V1.8.5 |
2.2 配置参数
1)配置EXTI IO中断,其用测监测编码器的冲击脉冲,选择PC0接口,同时要使能外部中断函数

使能中断函数

2)配置Timer7,中断间隔为10us,其具体配置参数如下:

使能中断函数

3)配置PWM相关的参数和使能通道

定时器相关的参数配置如下,计数周期为10ms

PWM通道相关的参数:

各个通道对应的IO接口如下:
2.3 生成项目
配置完成各个参数后,就可以生成项目,打开项目后,其结构如下:

3 PID算法实现
3.1 概念
PID是一种常用的控制算法,全名为比例-积分-微分控制算法(Proportional-Integral-Derivative Control)。它通过对系统的误差进行比例、积分和微分运算,从而对系统进行控制。
PID控制算法的基本原理是:根据当前系统的误差,分别计算比例、积分和微分项,并将它们加权叠加作为最终的控制量。
具体来说,比例项(Proportional)是根据误差的大小与比例系数的乘积来计算的,它决定了控制量与误差之间的直接关系。比例项越大,控制量的调整越快。
积分项(Integral)是根据误差的累积进行计算的,它可以消除系统存在的静态误差,并且对于系统的稳定性有所影响。积分项越大,控制量的调整越缓慢。
微分项(Derivative)是根据误差的变化率进行计算的,它可以预测误差的未来变化趋势,并提前调整控制量。微分项越大,控制量的调整越灵敏。
PID算法的最终控制量是比例项、积分项和微分项的加权叠加,其中比例系数、积分系数和微分系数可以根据实际需求进行调整,以达到最佳的控制效果。
理想的PID控制算法:
• Kp —— 比例增益, Kp 与比例度成倒数关系
• Tt —— 积分时间常数
• TD —— 微分时间常数
• u(t)—— PID 控制器的输出信号
• e(t)—— 给定值 r(t)与测量值误差
3.2 代码实现
代码117行: 计算目标值与实际值的误差
代码124行:累计误差值
代码127行:实现PID的功能
代码130行: 传递误差值

实际代码:
typedef struct
{float target_val; //目标值float actual_val; //实际值float err; //定义偏差值float err_last; //定义上一个偏差值float Kp,Ki,Kd; //定义比例、积分、微分系数float integral; //定义积分值
}_pid;/*** @brief 速度PID算法实现* @param actual_val:实际值@note 无* @retval 通过PID计算后的输出*/
float pid_speed_realize(_pid *pid, float actual_val)
{/*计算目标值与实际值的误差*/pid->err = pid->target_val - actual_val;if((pid->err<0.2f )&& (pid->err>-0.2f)){pid->err = 0.0f;}pid->integral += pid->err; // 误差累积/*PID算法实现*/pid->actual_val = pid->Kp*pid->err+pid->Ki*pid->integral+pid->Kd*(pid->err-pid->err_last);/*误差传递*/pid->err_last=pid->err;/*返回当前实际值*/return pid->actual_val;
}
4 其他功能实现
4.1 设置电机速度
代码80行: 设置通道1的占空比值
代码81行: 设置通道2的占空比值为0,用于控制方向

实际代码:
void set_motor_speed( uint16_t actual_speed )
{HAL_TIM_SetPWM_Pulse( actual_speed, TIM_CHANNEL_1);HAL_TIM_SetPWM_Pulse( 0, TIM_CHANNEL_2);
}
4.2 PID算法控制电机
代码195行:获取当前电机的转速
代码198行:比较实际值和期望值的差值,便于将实际值控制在一定的范围之内
代码201行:使用实际值进行PID运行,计算出占空比的值,以调节转速
代码205行:设置电机速度

实际代码:
void motor_pid_control(void)
{float actual_speed, cal_speed ;uint8_t value;bool is_match;uint8_t buff[16];uint32_t delta_value;actual_speed = get_motor_speed();cal_speed = pid_get_target(&pid_speed);is_match = abs((int)((actual_speed- cal_speed)*10)) > 10 ? false : true;if( !is_match ){cal_speed = pid_speed_realize( &pid_speed,actual_speed); // 进行 PID 计算cal_speed = convet_speed( cal_speed );cal_speed = (cal_speed > PWM_PERIOD_MAX_COUNT) ? PWM_PERIOD_MAX_COUNT : cal_speed; // 速度上限处理set_motor_speed(cal_speed); // 设置 PWM 占空比}#if defined(PID_ASSISTANT_EN)value = (uint8_t)actual_speed;buff[0] = value;protocol_computer_value(SEND_FACT_CMD, CURVES_CH1, buff, 1); // 给通道 1 发送实际值#elseprintf("实际值:%.02f 目标值:%.0f\n", actual_speed, pid_get_target(&pid_speed)); // 打印实际值和目标值#endif
}
4.3 功能函数的调用
代码211行:计算电机的转速
代码217行:电机PID控制函数

实际源码:
void motor_pid_control(void)
{float actual_speed, cal_speed ;uint8_t value;bool is_match;uint8_t buff[16];uint32_t delta_value;actual_speed = get_motor_speed();cal_speed = pid_get_target(&pid_speed);is_match = abs((int)((actual_speed- cal_speed)*10)) > 10 ? false : true;if( !is_match ){cal_speed = pid_speed_realize( &pid_speed,actual_speed); // 进行 PID 计算cal_speed = convet_speed( cal_speed );cal_speed = (cal_speed > PWM_PERIOD_MAX_COUNT) ? PWM_PERIOD_MAX_COUNT : cal_speed; // 速度上限处理set_motor_speed(cal_speed); // 设置 PWM 占空比}#if defined(PID_ASSISTANT_EN)value = (uint8_t)actual_speed;buff[0] = value;protocol_computer_value(SEND_FACT_CMD, CURVES_CH1, buff, 1); // 给通道 1 发送实际值#elseprintf("实际值:%.02f 目标值:%.0f\n", actual_speed, pid_get_target(&pid_speed)); // 打印实际值和目标值#endif
}
5 测试
5.1 测试案例1
PID参数设置如下类型,观察速度值的变化(Expect value: speed = 50 )
pid_speed.Kp = 7.0;pid_speed.Ki = 20.0;pid_speed.Kd = 14.0;
串口log如下,在5s左右就完成速度定速功能

5.2 测试案例2
PID参数设置如下类型,观察速度值的变化(Expect value: speed = 50 )
pid_speed.Kp = 7.0;pid_speed.Ki = 2.0;pid_speed.Kd = 4.0;
串口log如下,在2min左右才完成速度定速功能


相关文章:
PID算法在电机速度控制上的应用
目录 概述 1 系统硬件框架 1.1 框架介绍 1.2 硬件实物图 2 STM32Cub生成工程 2.1 软件版本信息 2.2 配置参数 编辑2.3 生成项目 3 PID算法实现 3.1 概念 3.2 代码实现 4 其他功能实现 4.1 设置电机速度 4.2 PID算法控制电机 4.3 功能函数的调用 5 测试 5.1 …...
埃隆·马斯克 - 从梦想家到改变世界的企业家
埃隆马斯克 - 从梦想家到改变世界的企业家 本文内容是埃隆马斯克传的重点章节精华提炼,介绍了马斯克传奇一生 参考资料内容:埃隆马斯克传&造梦者埃隆马斯克 参考资料在文末获取,关注我,分享优质前沿资料(IT、运…...
微信小程序长图片自适应
/*wxss中的代码*/ .image-container { display:flex;width: 100%; /* 或其他需要的宽度 */ /* margin-bottom: 10px; //图片之间的间距 */height: auto; } 核心:要真正自适应,就要在wxml中加入固定宽度style“width:750rpx” /*wxml中的代码*/ &l…...
elasticsearch hanlp 插件安装操作
elasticsearch hanlp 插件安装操作 下载 hanlp 插件上传hanlp插件到elasticsearch服务器安装hanlp插件kibana测试 下载 hanlp 插件 这里大家根据自己对应的 elasticsearch 版本下载匹配版本的 hanlp 插件,由于 hanlp 及 elasticsearch 各个版本之间差别较大&#x…...
为什么进程和线程 ID 总是 4 的倍数?
如果您研究下任务管理器中的的进程 ID (PID),则你会发现这样一个规律:它们都是 4 的倍数。 基于 Windows NT 内核的操作系统上,不止是进程 ID,实际上,线程 ID (TID) 也遵守这样的规律:也即它们都是 4 的倍…...
LabVIEW版本控制
LabVIEW作为一种流行的图形化编程环境,在软件开发中广泛应用。有效地管理版本控制对于确保软件的可靠性和可维护性至关重要。LabVIEW提供了多种方式来管理VI和应用程序的修订历史,以满足不同规模和复杂度的项目需求。 LabVIEW中的VI修订历史 LabVIEW内置…...
不输Kimi的AI插件——Elmo Chat (免费,无需注册)
🌚 前阵子不是写了篇《一分钟上手AI神器——Kimi (附_ 官方提示词)》 嘛,给大伙安利了一波 Kimi Chat 这个AI 神器,不知道是不是用户量上来了,算力一下子跟不上,感觉变笨了不少🤣。在别的推文看到多轮对话后…...
使用cesiumLab使shp转为3dtlies
过程不做赘述,网上大把,说下注意事项。 1. 存储3DTiles 选项 若是打开则输出的文件为glb格式文件,因为glb文件好储存易传输跨平台。cesium可以使用但无法处理,例如改变颜色,改着色器等。若是不打开则输出的文件为bm3d格式文件,此…...
中科数安 | 透明加密防泄密系统!如何有效防止企业内部核心数据资料外泄?
中科数安提供的透明加密防泄密系统是一种专为企业设计的数据保护解决方案,它通过以下关键特性有效防止企业内部核心数据资料外泄: PC地址:——www.weaem.com 自动智能透明加密:系统能够在操作系统级别无缝集成,对指定类…...
go的反射和断言
在go中对于一个变量,主要包含两个信息变量类型(type)和变量值(value) 可以通过reflect包在运行的时候动态获取变量信息,并能够进行操作 对于Type可以通过reflect.TypeOf()获取到变量的类型信息 reflect.Ty…...
打造新引擎,迈向数智金融新未来
数智技术正在全面赋能金融机构转型升级以及促进金融与实体经济的加速融合,已呈现出金融机构数智化经营加速、产业 数字金融深度融合、数字技术驱动绿色金融发展、金融信创成果涌现、金融机构加快数字化组织管理变革等行业趋势。 根据银行业协会调研,78%…...
广东智慧物流2024年端午节放假安排
广东智慧物流2024年端午节放假安排...
Facebook的隐私保护挑战:用户数据安全的新时代
在全球范围内,Facebook已经成为了不可忽视的社交媒体巨头,它连接着超过20亿的活跃用户。然而,随着其影响力的不断扩大,关于用户隐私和数据安全的问题也愈加引人关注。本文将深入探讨Facebook面临的隐私保护挑战,以及它…...
Gradio.NET:一个快速制作演示demo网页的利器
Gradio介绍 Gradio是一个用于创建机器学习模型交互界面的Python库。它允许开发者快速为他们的模型创建一个简单的web界面,以便于非技术用户和其他开发者进行交互和测试。 Gradio的主要优点是易用性和灵活性。你只需要几行代码就可以为你的模型创建一个交互界面。你…...
001 IOC与DI(有点杂)
文章目录 IOC与DI区别联系总结 依赖注入解耦管理对象的生命周期提高配置灵活性三种注入方式不可变对象的设计 构造器注入Setter方法注入字段注入Setter方法注入为什么不破坏封装性字段注入为什么破坏封装性为什么将字段或setter方法设置为private?总结 setter方法注…...
Python语言自学:深入探索四个基础、五个进阶、六个实战及七个挑战
Python语言自学:深入探索四个基础、五个进阶、六个实战及七个挑战 Python,作为一种通用编程语言,其简洁的语法、丰富的库和强大的功能,使得越来越多的人选择自学Python。但自学之路并非坦途,本文将从四个方面、五个方…...
运维开发介绍
目录 1.什么是运维开发 2.作用 3.优点 4.缺点 5.应用场景 5.1.十个应用场景 5.2.网站和Web应用程序 6.案例 7.小结 1.什么是运维开发 运维开发(DevOps)是一种结合软件开发(Development)与信息技术运维(Opera…...
Mac版的Typora的安装和激活(亲测可用哦~~~)
星光下的赶路人star的个人主页 珍视生活中的苦与乐,悦纳生活的悲伤离合 文章目录 1.下载2.安装3.激活4.注意点 1.下载 直接官网下载即可!!! 官网地址:typora官网 2.安装 直接拖进去安装即可 3.激活 1.利用访达进入…...
【Python系列】Python 方法变量参数详解
💝💝💝欢迎来到我的博客,很高兴能够在这里和您见面!希望您在这里可以感受到一份轻松愉快的氛围,不仅可以获得有趣的内容和知识,也可以畅所欲言、分享您的想法和见解。 推荐:kwan 的首页,持续学…...
生命在于学习——Python人工智能原理(3.2)
三、深度学习 (二)人工神经网络 人工神经网络是模仿人类大脑神经系统工作原理所创建的数学模型,有并行的分布处理能力、高容错性和自我学习等特征。 1、感知器 感知器由Frank Roseblatt于1957年提出,是一种广泛使用的线性分类…...
简易版抽奖活动的设计技术方案
1.前言 本技术方案旨在设计一套完整且可靠的抽奖活动逻辑,确保抽奖活动能够公平、公正、公开地进行,同时满足高并发访问、数据安全存储与高效处理等需求,为用户提供流畅的抽奖体验,助力业务顺利开展。本方案将涵盖抽奖活动的整体架构设计、核心流程逻辑、关键功能实现以及…...
django filter 统计数量 按属性去重
在Django中,如果你想要根据某个属性对查询集进行去重并统计数量,你可以使用values()方法配合annotate()方法来实现。这里有两种常见的方法来完成这个需求: 方法1:使用annotate()和Count 假设你有一个模型Item,并且你想…...
python爬虫:Newspaper3k 的详细使用(好用的新闻网站文章抓取和解析的Python库)
更多内容请见: 爬虫和逆向教程-专栏介绍和目录 文章目录 一、Newspaper3k 概述1.1 Newspaper3k 介绍1.2 主要功能1.3 典型应用场景1.4 安装二、基本用法2.2 提取单篇文章的内容2.2 处理多篇文档三、高级选项3.1 自定义配置3.2 分析文章情感四、实战案例4.1 构建新闻摘要聚合器…...
Springcloud:Eureka 高可用集群搭建实战(服务注册与发现的底层原理与避坑指南)
引言:为什么 Eureka 依然是存量系统的核心? 尽管 Nacos 等新注册中心崛起,但金融、电力等保守行业仍有大量系统运行在 Eureka 上。理解其高可用设计与自我保护机制,是保障分布式系统稳定的必修课。本文将手把手带你搭建生产级 Eur…...
(转)什么是DockerCompose?它有什么作用?
一、什么是DockerCompose? DockerCompose可以基于Compose文件帮我们快速的部署分布式应用,而无需手动一个个创建和运行容器。 Compose文件是一个文本文件,通过指令定义集群中的每个容器如何运行。 DockerCompose就是把DockerFile转换成指令去运行。 …...
NXP S32K146 T-Box 携手 SD NAND(贴片式TF卡):驱动汽车智能革新的黄金组合
在汽车智能化的汹涌浪潮中,车辆不再仅仅是传统的交通工具,而是逐步演变为高度智能的移动终端。这一转变的核心支撑,来自于车内关键技术的深度融合与协同创新。车载远程信息处理盒(T-Box)方案:NXP S32K146 与…...
push [特殊字符] present
push 🆚 present 前言present和dismiss特点代码演示 push和pop特点代码演示 前言 在 iOS 开发中,push 和 present 是两种不同的视图控制器切换方式,它们有着显著的区别。 present和dismiss 特点 在当前控制器上方新建视图层级需要手动调用…...
android13 app的触摸问题定位分析流程
一、知识点 一般来说,触摸问题都是app层面出问题,我们可以在ViewRootImpl.java添加log的方式定位;如果是touchableRegion的计算问题,就会相对比较麻烦了,需要通过adb shell dumpsys input > input.log指令,且通过打印堆栈的方式,逐步定位问题,并找到修改方案。 问题…...
CSS3相关知识点
CSS3相关知识点 CSS3私有前缀私有前缀私有前缀存在的意义常见浏览器的私有前缀 CSS3基本语法CSS3 新增长度单位CSS3 新增颜色设置方式CSS3 新增选择器CSS3 新增盒模型相关属性box-sizing 怪异盒模型resize调整盒子大小box-shadow 盒子阴影opacity 不透明度 CSS3 新增背景属性ba…...
篇章一 论坛系统——前置知识
目录 1.软件开发 1.1 软件的生命周期 1.2 面向对象 1.3 CS、BS架构 1.CS架构编辑 2.BS架构 1.4 软件需求 1.需求分类 2.需求获取 1.5 需求分析 1. 工作内容 1.6 面向对象分析 1.OOA的任务 2.统一建模语言UML 3. 用例模型 3.1 用例图的元素 3.2 建立用例模型 …...

