说到PID算法,想必大部人并不陌生,PID算法在很多方面都有重要应用,比如电机的速度控制,恒温槽的温度控制,四轴飞行器的平衡控制等等,作为闭环控制系统中的一种重要算法,其优点和可实现性都成为人们的首选。下面简单来讲解一下PID算法:

首先PID算法是有比例,积分,微分三部分组成,先说下比例部分,所谓比例部分,就是呈线性关系,举个例子,一个电热丝加热水,开始的时候温度很低,离50℃很大,这时应该加大功率,离目标温度越大,其功率应该越大,反之越小,这就是比例部分。

乍一看,既然比例部分已经可以控制温度了为啥还需要积分和微分部分呢,难道是多此一举么?其实不然,在实际中会出现这种情况,当加热到50℃时,系统很难停止下来,而是会持续一段时间,这样就会超过预设值,所以仅有比例控制并不完美,这是就需要积分部分和微分部分。积分部分就是把之前的误差全部累加起来,这样起始时由于误差很大加热功率就大,随着接近预设值后功率开始减少,微分部分就是起始时温度增加很快,表示此时需要很大的功率,随着温度接近预设值,其斜率开始减小最后为零,意味着功率也减少,当然很难为零,一般在一定的范围内波动。

现在开始用C语言来实现PID算法:

位置式:

比例部分

    Kp:比例系数  SetValue:预设值  FactValue:当前实际值  Error_1:当前误差

则比例部分为:

    Sp  =   Kp*(SetValue - FactValue)

或者

    Sp  =  Kp*Error_1

注解:Sp大小反应需要控制的量大小,比如Sp越大,功率越大。当Sp为负值时,表示要超过预设值,如果是电机,则需要反转

积分部分

    Ki:积分系数  Error_1:当前误差  Error_2:上一次误差  Error_3:上上一次误差  ........Error_n:开始时的误差

则积分部分为:

    Si  =  Ki*(Error_1+Error_2+Error_3+......+Error_n)

注解:因为整个是一个过程,所以上一次误差其实就是上一次的当前误差

微分部分

    Kd:微分系数  Error_1:当前误差  Error_2:上一次误差 

则微分部分为:

    Sd  =  Kd*(Error_1-Error_2)

综上部分的PID得:

    PID=Sp + Si + Sd = Kp*Error_1 + Ki*(Error_1+Error_2+Error_3+......+Error_n) + Kd*(Error_1-Error_2)

增量式

将上述推导的PID记作时间为k时刻的PID控制量,则

    PID(k) =Sp + Si + Sd = Kp*Error_1(k) + Ki*(Error_1(k)+Error_2(k-1)+Error_3(k-2)+......+Error_n(0)) + Kd*(Error_1(k)-Error_2(k-1))        1

将上式k=k-1代入得:

    PID(k-1) =Sp + Si + Sd = Kp*Error_1(k-1) + Ki*(Error_1(k-1)+Error_2(k-2)+Error_3(k-3)+......+Error_n(0)) + Kd*(Error_1(k-1)-Error_2(k-2))               2

1-2得:

    PID(k) - PID(k-1) =  Kp*(Error_1(k)-Error_1(k-1)) + Ki*(Error_1(k)) + Kd*(Error_1(k)-2*Error_2(k-1)+Error_2(k-2))

PID(k) - PID(k-1)记作detPID

    detPID = Kp*(Error_1(k)-Error_1(k-1)) + Ki*(Error_1(k)) + Kd*(Error_1(k)-2*Error_2(k-1)+Error_2(k-2))

这样就得到了增量式的PID算法,其计算的结果为增加的控制量

增量式的PID有个好处就是只与当前三个误差量有关系,与其他无关,这样就简化的处理过程,而且提高了精度,下面是PID源码:

/*文件名:PID.h*/

#ifndef  _PID_H_
#define _PID_H_ extern float Kp,Ki,Kd; //系数(全局变量)
extern float AclValue; //实际值
extern float SetValue; int PID(void); #endif
/*########################################################################
文件名:PID.c
时间: 2018.9.7
备注:无
#########################################################################*/ #include "PID.h" float Kp=,Ki=0.8,Kd=0.5; //系数 float SetValue=; //设定值 float AclValue=; //实际 float Error1=,Error2=,Error3=; //误差 /* 下面为增量式PID算法 */ /**********************************************************************************
函数名:PID
返回值:输出增量
参数:无
备注:当输出大于0表示小于预设值,当输出小于0表示大于预设值
***********************************************************************************/
int PID(void)
{
float OutValue =;
Error3 = SetValue - AclValue; OutValue = Kp*(Error3-Error2)+Ki*(Error3)+Kd*(Error3-*Error2+Error1); Error1=Error2; //这部分是迭代,因为上次的误差就是上次的当前误差
Error2=Error3; if(OutValue>) //这部分是规定最大输出增量
OutValue=;
if(OutValue<-)
OutValue=-; return OutValue;
}

下面给出计算机模拟代码;

#include "stdio.h"

float Kp=,Ki=,Kd=0.5;  //系数

float SetValue=;  //设定值

float AclValue=; //实际

float Error1=,Error2=,Error3=;     //误差

/*  下面为增量式PID算法  */

/**********************************************************************************
函数名:PID
返回值:输出增量
参数:无
备注:当输出大于0表示小于预设值,当输出小于0表示大于预设值
***********************************************************************************/
int PID(void)
{
float OutValue =;
Error3 = SetValue - AclValue; OutValue = Kp*(Error3-Error2)+Ki*(Error3)+Kd*(Error3-*Error2+Error1); Error1=Error2;
Error2=Error3; return OutValue;
} int main(void)
{
unsigned int i=;
while(i)
{ PID(); //特别注意这里:必须要运行,因为需要执行这一步:Error1=Error2; Error2=Error3; printf("当前实际值为:%f \n",AclValue); AclValue += PID(); i--);
    } 

    return ;
}

运行结果:

    

单片机之PID算法的更多相关文章

  1. PID算法笔记2

    总所周知,PID算法是个很经典的东西.而做自平衡小车,飞行器PID是一个必须翻过的坎.因此本节我们来好好讲解一下PID,根据我在学习中的体会,力求通俗易懂.并举出PID的形象例子来帮助理解PID.一. ...

  2. PID算法通俗理解,平衡车,倒立摆,适合不理解PID算法的人来看!

    先插句广告,本人QQ522414928,不熟悉PID算法的可以一起交流学习,随时在线(PID资料再我的另一篇博客里) 倒立摆资料连接↓ https://www.cnblogs.com/LiuXinyu ...

  3. PID算法原理 一图看懂PID的三个参数

    找了好久这一篇算是很容易看懂的了  推荐给大家   写的十分清楚   原文作者DF创客社区virtualwiz LZ以前有个小小的理想,就是让手边的MCU自己"思考"起来,写出真正 ...

  4. 线性控制原理——PID算法应用

    使用控制系统(PID)控制被控对象 PID控制的三要素:控制器,被控对象,反馈器.控制器就是一个数学模型,就PID来说,等同于PID算法.是对反馈量的一个处理与输出.通俗的说就是对于每个被控的量,我的 ...

  5. PID算法学习记录

    最近做项目需要用到PID算法,这个本来是我的专业(控制理论与控制工程),可是我好像是把这个东西全部还给老师了. 没办法,只好抽时间来学习了. 先占个座,后续将持续更新!

  6. 位置式PID与增量式PID算法

    位置式PID与增量式PID算法  PID控制是一个二阶线性控制器     定义:通过调整比例.积分和微分三项参数,使得大多数的工业控制系统获得良好的闭环控制性能.     优点             ...

  7. PID算法

    所谓PID就是比例-积分-微分的英文缩写,但并不是必须同时具备这三种算法,也可以是 PD, PI,甚至只有 P算法控制,下面分别介绍每个参数的含义:首先需要明确一个事实就是,要实现PID算法,必须在硬 ...

  8. PID算法(c 语言)(转)

    PID算法(c 语言)(来自老外) #include <stdio.h> #include<math.h> //定义PID 的结构体 struct _pid { int pv; ...

  9. PID控制器开发笔记之一:PID算法原理及基本实现

    在自动控制中,PID及其衍生出来的算法是应用最广的算法之一.各个做自动控制的厂家基本都有会实现这一经典算法.我们在做项目的过程中,也时常会遇到类似的需求,所以就想实现这一算法以适用于更多的应用场景. ...

随机推荐

  1. SpringBoot中常用注解@Controller/@RestController/@RequestMapping的区别

    @Controller 处理http请求 @Controller //@ResponseBody public class HelloController { @RequestMapping(valu ...

  2. Spring中Bean及@Bean的理解

    Spring中Bean及@Bean的理解 Bean在Spring和SpringMVC中无所不在,将这个概念内化很重要,下面分享一下我的想法: 一.Bean是啥 1.Java面向对象,对象有方法和属性, ...

  3. 通过yum安装php7

    Linux下全局安装composer方法: //下载composercurl -sS https://getcomposer.org/installer | php //将composer.phar文 ...

  4. Vue.js连接后台数据jsp页面  ̄▽ ̄

    <%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding= ...

  5. 把post请求的地址粘贴到浏览器地址栏敲回车报错405[Method Not Allowed]

    为什么把post请求的地址粘贴到浏览器地址栏敲回车会报405?原因:在浏览器地址栏敲回车,浏览器默认是以get方式发送请求,而你的请求是post,这样当然会报405了: 405:方法不允许,不支持ge ...

  6. java MD5/AES/DES加解密汇总

    package com.test.test1.util; import java.security.MessageDigest; import java.security.SecureRandom; ...

  7. Html转成Image

    html转图片,原来用了html2image.jar,但是做不到复杂的css js渲染效果. 在网友推荐下,可以用wkhtmltoimage插件,这是用谷歌浏览器的内核webkit,网上搜一下可以下载 ...

  8. 特大数字之和,返回结果是字符串(考虑到数字特别大,如果相加会产生e)

    自己做的,没有整理代码,还是做出来了: 做这个题时,最总要的一步思路就是,先让长度一致,然后从个位开始,每一个与每一个数字相加,如果大于10,则下一次另外两个数相加时加1 function add(a ...

  9. servlet中的请求响应与重定向区别

    一.概念 请求响应(转发):将客户端请求转发另一个servlet或者jsp页面------------------------getRequestDispatcher()方法 重定向: 返回一个连接给 ...

  10. Mysql添加新用户遇到的一些小问题

    登陆命令:mysql -u root -p 添加本地用户:create user  'sheet'@'localhost' identified by '123456' ; 添加允许外网IP访问的用户 ...