杂谈PID控制算法——最终篇:C语言实现51单片机中的PID算法
真遗憾,第二篇章没能够发表到首页上去。趁热打铁。把最终篇——代码篇给发上来。
代码的设计思想请移步前两篇文章
//pid.h
#ifndef __PID__
#define __PID__
/*PID = Uk + KP*[E(k)-E(k-1)]+KI*E(k)+KD*[E(k)-2E(k-1)+E(k-2)];(增量型PID算式)
函数入口: RK(设定值),CK(实际值),KP,KI,KD
函数出口: U(K)*/
typedef struct PIDValue
{
int8 KP;
int8 KI;
int8 KD;
int8 F;
int8 BITMOV;
int EK[3]; int UK;
int RK;
int CK;
int UK_REAL; }pid_str;
//PIDValueStr PID;
void pid_exe(pid_str *PID) ;
#endif //pid.c
/*PID = PID->UK_REAL + PID->KP*[E(k)-E(k-1)]+PID->KI*E(k)+PID->KD*[E(k)-2E(k-1)+E(k-2)];(增量型PID算式)
函数入口: PID->RK(设定值),PID->CK(实际值),PID->KP,PID->KI,PID->KD
函数出口: U(K)*/
#include"defines.h"
#include"pid.h"
#define MAXOUT 0xff
//#define MAXGAP 100 void pid_exe(pid_str*PID)
{
PID->EK[2]=PID->EK[1];
PID->EK[1]=PID->EK[0];
PID->EK[0]=PID->RK-PID->CK;
PID->UK_REAL=PID->UK_REAL
+PID->KP*(PID->EK[0]-PID->EK[1])//微分一次后积分即原数
+(float)PID->KI*PID->EK[0]/PID->F//直接积分
+(float)PID->KD*(PID->EK[0]-2*PID->EK[1]+PID->EK[2])*PID->F;//二阶微分后积分即一阶微分
if((PID->UK_REAL>>PID->BITMOV)>=MAXOUT)
{
PID->UK=MAXOUT;
}else if(PID->UK_REAL>>PID->BITMOV<=-MAXOUT)
{
PID->UK=-MAXOUT;
}else
{
PID->UK=PID->UK_REAL>>PID->BITMOV;
} }
这里我写的代码用到的是增量型的PID(即UK_REAL + PID->KP*[E(k)-E(k-1)]+PID->KI*E(k)+PID->KD*[E(k)-2E(k-1)+E(k-2)];这句话所对应的是pid控制量在之前pid控制量的基础上增加的值,相当于求了一次导)。最终输出的结果将每一次运算的值累加输出就行了。
附上摘抄的位置型pid与增量型pid的区别来。。
(1)位置式PID控制的输出与整个过去的状态有关,用到了误差的累加值;而增量式PID的输出只与当前拍和前两拍的误差有关,因此位置式PID控制的累积误差相对更大; (2)增量式PID控制输出的是控制量增量,并无积分作用,因此该方法适用于执行机构带积分部件的对象,如步进电机等,而位置式PID适用于执行机构不带积分部件的对象,如电液伺服阀。 (3)由于增量式PID输出的是控制量增量,如果计算机出现故障,误动作影响较小,而执行机构本身有记忆功能,可仍保持原位,不会严重影响系统的工作,而位置式的输出直接对应对象的输出,因此对系统影响较大。
PS:之前模板看的审美疲劳了。。换个模板换个心情。。
PPS:求小编给力。。求过。。。
杂谈PID控制算法——最终篇:C语言实现51单片机中的PID算法的更多相关文章
- 杂谈PID控制算法——第一篇:三个量
电赛训练了大半个暑假,人渐渐开始进入到了疲倦期.既然这样那就好好休息下自己也好吧. 休息也不能光休息,乘机把平常写过的一些东西好好整理也好. 从第一次训练开始我们就接触到了一个新的名词——PID控制理 ...
- c语言编写51单片机中断程序,执行过程是怎样的?
Q:c语言编写51单片机中断程序,执行过程是怎样的? 例如程序:#include<reg52.h> void main(void) { EA=1; //开放总中断 E ...
- 杂谈PID控制算法——第二篇:调·三个量
上面一篇文章讲了一下PID算法中的三个常量大致的在PID算法中起的一个作用,但在实际的使用中,究竟应该如何调节(或者用更加专业的话说是整定)PID控制算法的三个.首先可以将KP,KI,KD三个常量全部 ...
- 一文读懂PID控制算法(抛弃公式,从原理上真正理解PID控制)
PID控制应该算是应用非常广泛的控制算法了.小到控制一个元件的温度,大到控制无人机的飞行姿态和飞行速度等等,都可以使用PID控制.这里我们从原理上来理解PID控制. PID(proportion ...
- PID控制算法的C语言实现
参考: PID控制器开发笔 浅谈位置式PID 专家PID控制在快速系统中的仿真及应用(这篇了论文介绍的积分分离PID.专家PID(脚本实现和simulink实现)很详细) PID控制算法的C语言实现一 ...
- PID控制算法的C语言实现十 专家PID与模糊PID的C语言实现
本节是PID控制算法的C语言实现系列的最后一节,前面8节中,已经分别从PID的实现到深入的过程进行了一个简要的讲解,从前面的讲解中不难看出,PID的控制思想非常简单,其主要问题点和难点在于比例.积分. ...
- PID控制算法的C语言实现十一 模糊算法简介
在PID控制算法的C语言实现九中,文章已经对模糊PID的实质做了一个简要说明.本来打算等到完成毕业设计,工作稳定了再着力完成剩下的部分.鉴于网友的要求和信任,抽出时间来,对模糊PID做一个较为详细的论 ...
- PID控制算法的C语言实现一 PID算法原理
本系列是转载............. 全部的程序有一个共同点:就是我没认真去调pid的参数 在工业应用中PID及其衍生算法是应用最广泛的算法之一,是当之无愧的万能算法,如果能够熟练掌握PID算法的设 ...
- PID控制算法的c语言实现十二 模糊PID的参数整定
这几天一直在考虑如何能够把这一节的内容说清楚,对于PID而言应用并没有多大难度,按照基本的算法设计思路和成熟的参数整定方法,就算是没有经过特殊训练和培训的人,也能够在较短的时间内容学会使用PID算法. ...
随机推荐
- 动态规划:LCS
先上状态转移方程,还是很容易看明白的 例题是Codevs的1862,这个题不是实现了方程就可以了的,还要完成一个事情那就是计数,数一数到底有多少个最长公共子序列 #include<cstdio& ...
- 计算代码行数Demo源码
源码下载:04-计算代码行数.zip24.1 KB//// main.m// 计算代码行数//// Created by apple on 13-8-12.//技术博客http://www.cn ...
- DB 基本性能指标
DB: •500K I/O limit with kill(5M I/O limit for DWS) •10,000 return row limit with kill •30 seconds p ...
- 【Mysql优化】聚簇索引与非聚簇索引概念
必须为主键字段创建一个索引,这个索引就是所谓的"主索引".主索引与唯一索引的唯一区别是:前者在定义时使用的关键字是PRIMARY而不是UNIQUE. 首先明白两句话: innod ...
- measure time program
#include <time.h> int delay(int time) { int i,j; for(i =0;i<time;i++) for(j=0;j<10000;j+ ...
- appium===Python+Appium环境部署教程
*前提是你已经安装好python,以及python的pip工具 *安装python请自行百度教程~ 1.安装安卓sdk 安装包:http://tools.android-studio.org/inde ...
- Android之进程通信--Binder
Cilent从ServiceManger哪里获得BnMediaService的BnBinder引用就可以调用BnMediaPlayerService的方法了,BnMediaPlayerService是 ...
- Java常见知识点(一)
1.+不仅可作为加法运算符使用,还可作为字符串连接运算符使用. 2.a = b = c = 7;//虽然java支持这种一次为多个变量赋值的写法,但这种写法导致程序的可读性降低,因此不推荐这样写. ...
- webpack-dev-server坑
转载人家滴 https://segmentfault.com/q/1010000007561947/a-1020000007596130 需要webpack开发服务(webpack-dev-serve ...
- Eclipse svn代码提交冲突
Eclipse svn代码提交冲突(转) 1.Synchronize视图下查看代码冲突 1.Incoming Mode 全部update,更新到本地2.Outgoing Mode 全部commit,提 ...