改进初学者的PID-正反作用

最近看到了Brett Beauregard发表的有关PID的系列文章,感觉对于理解PID算法很有帮助,于是将系列文章翻译过来!在自我提高的过程中,也希望对同道中人有所帮助。作者Brett Beauregard的原文网址:http://brettbeauregard.com/blog/2011/04/improving-the-beginners-pid-direction/

 

1、问题所在

将PID连接过程分为两组:直接作用和反向作用。到目前为止,我所展示的所有例子都是直接行动。也就是说,输出的增加会导致输入的增加。对于反向作用过程,情况正好相反。例如,在冰箱中,冷却水的增加会导致温度下降。要使初学者 PID 使用反向过程,kp、ki 和 kp 的符号都必须为负数。

这本身不是问题,但用户必须选择正确的符号,并确保所有参数都具有相同的符号。

2、解决方案

为了让这个过程简单一点,我要求 kp、ki 和 kp 都是大于等于0的。如果用户连接到反向进程,则使用SetControllerDirection函数指定反向进程。这可以确保所有参数都具有相同的符号,并使事情操作起来更直观。

3、代码

/*working variables*/
unsigned long lastTime;
double Input,Output,Setpoint;
double ITerm,lastInput;
double kp,ki,kd;
int SampleTime = 1000;//1 sec
double outMin,outMax;
bool inAuto = false;#define MANUAL 0
#define AUTOMATIC 1#define DIRECT 0
#define REVERSE 1
int controllerDirection = DIRECT;void Compute()
{if(!inAuto) return;unsigned long now = millis();int timeChange = (now - lastTime);if(timeChange>=SampleTime){/*Compute all the working error variables*/double error = Setpoint - Input;ITerm+= (ki * error);if(ITerm > outMax) ITerm= outMax;else if(ITerm < outMin) ITerm= outMin;double dInput = (Input - lastInput);/*Compute PID Output*/Output = kp * error + ITerm- kd * dInput;if(Output > outMax) Output = outMax;else if(Output < outMin) Output = outMin;/*Remember some variables for next time*/lastInput = Input;lastTime = now;}
}void SetTunings(double Kp,double Ki,double Kd)
{if (Kp<0 || Ki<0|| Kd<0) return;double SampleTimeInSec = ((double)SampleTime)/1000;kp = Kp;ki = Ki * SampleTimeInSec;kd = Kd / SampleTimeInSec;if(controllerDirection ==REVERSE){kp = (0 - kp);ki = (0 - ki);kd = (0 - kd);}
}void SetSampleTime(int NewSampleTime)
{if (NewSampleTime > 0){double ratio  = (double)NewSampleTime/(double)SampleTime;ki *= ratio;kd /= ratio;SampleTime = (unsigned long)NewSampleTime;}
}void SetOutputLimits(double Min,double Max)
{if(Min > Max) return;outMin = Min;outMax = Max;if(Output > outMax) Output = outMax;else if(Output < outMin) Output = outMin;if(ITerm > outMax) ITerm= outMax;else if(ITerm < outMin) ITerm= outMin;
}void SetMode(int Mode)
{bool newAuto = (Mode == AUTOMATIC);if(newAuto == !inAuto){  /*we just went from manual to auto*/Initialize();}inAuto = newAuto;
}void Initialize()
{lastInput = Input;ITerm = Output;if(ITerm > outMax) ITerm= outMax;else if(ITerm < outMin) ITerm= outMin;
}void SetControllerDirection(int Direction)
{controllerDirection = Direction;
}

4PID 完成

差不多结束了。我们已经把“初学者的PID”变成了我目前知道的最健壮的控制器。对于那些正在寻找PID库的详细解释的读者,我希望您得到了您想要的。对于那些正在编写自己的PID的人,我希望您能够收集到一些想法,这些想法可以为您节省一些时间。

最后说明两点:

  1. 如果这个系列中的东西看起来不对,请告诉我。我可能错过了什么,或者可能只需要在我的解释中更清楚。无论哪种方式,我都想知道。
  2. 这只是一个基本的PID。为了简单起见,我有意省略了许多其他问题。在我的脑海中:前馈,重置平铺,整数数学,不同的PID形式,使用速度而不是位置。如果有兴趣让我探讨这些话题,请让我知道。

欢迎关注:

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/499396.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

改进初学者的PID-测量的比例介绍

最近看到了Brett Beauregard发表的有关PID的系列文章&#xff0c;感觉对于理解PID算法很有帮助&#xff0c;于是将系列文章翻译过来&#xff01;在自我提高的过程中&#xff0c;也希望对同道中人有所帮助。作者Brett Beauregard的原文网址&#xff1a;http&#xff1a;//brettb…

改进初学者的PID-测量的比例编码

最近看到了Brett Beauregard发表的有关PID的系列文章&#xff0c;感觉对于理解PID算法很有帮助&#xff0c;于是将系列文章翻译过来&#xff01;在自我提高的过程中&#xff0c;也希望对同道中人有所帮助。作者Brett Beauregard的原文网址&#xff1a;http&#xff1a;//brettb…

PID:我应该何时计算积分项?

最近看到了Brett Beauregard发表的有关PID的系列文章&#xff0c;感觉对于理解PID算法很有帮助&#xff0c;于是将系列文章翻译过来&#xff01;在自我提高的过程中&#xff0c;也希望对同道中人有所帮助。作者Brett Beauregard的原文网址&#xff1a;http&#xff1a;//brettb…

Arduino PID自整定库

最近看到了Brett Beauregard发表的有关PID的系列文章&#xff0c;感觉对于理解PID算法很有帮助&#xff0c;于是将系列文章翻译过来&#xff01;在自我提高的过程中&#xff0c;也希望对同道中人有所帮助。作者Brett Beauregard的原文网址&#xff1a;http&#xff1a;//brettb…

LwIP应用开发笔记之二:LwIP无操作系统UDP服务器

前面我们已经完成了LwIP协议栈基于逻辑的基本移植&#xff0c;在这一节我们将以RAW API来实现UDP服务器。 1、UDP协议简述 UDP协议全称是用户数据报协议&#xff0c;在网络中它与TCP协议一样用于处理数据包&#xff0c;是一种无连接的协议。在OSI模型中&#xff0c;处于传输层…

LwIP应用开发笔记之三:LwIP无操作系统UDP客户端

前一节我们实现了基于RAW API的UDP服务器&#xff0c;在接下来&#xff0c;我们进一步利用RAW API实现UDP客户端。 1、UDP协议简述 UDP协议全称是用户数据报协议&#xff0c;在网络中它与TCP协议一样用于处理数据包&#xff0c;是一种无连接的协议。在OSI模型中&#xff0c;处…

LwIP应用开发笔记之四:LwIP无操作系统TFTP服务器

前面我们已经实现了UDP的回环客户端和回环服务器的简单应用&#xff0c;接下来我们实现一个基于UDP的简单文件传输协议TFTP。 1、TFTP协议简介 TFTP是TCP/IP协议族中的一个用来在客户机与服务器之间进行简单文件传输的协议&#xff0c;提供不复杂、开销不大的文件传输服务。端…

LwIP应用开发笔记之五:LwIP无操作系统TCP服务器

前面我们实现了UDP服务器及客户端以及基于其上的TFTP应用服务器。接下来我们将实现同样广泛应用的TCP协议各类应用。 1、TCP简述 TCP&#xff08;Transmission Control Protocol 传输控制协议&#xff09;是一种面向连接的、可靠的、基于字节流的传输层通信协议&#xff0c;由…

LwIP应用开发笔记之六:LwIP无操作系统TCP客户端

上一篇我们基于LwIP协议栈的RAW API实现了一个TCP服务器的简单应用&#xff0c;接下来一节我们来实现一个TCP客户端的简单应用。 1、TCP简述 TCP&#xff08;Transmission Control Protocol 传输控制协议&#xff09;是一种面向连接的、可靠的、基于字节流的传输层通信协议&a…

LwIP应用开发笔记之七:LwIP无操作系统HTTP服务器

前面我们实现了TCP服务器和客户端的简单应用&#xff0c;接下来我们实现一个基于TCP协议的应用协议&#xff0c;那就是HTTP超文本传输协议。 1、HTTP协议简介 超文本传输协议&#xff08;Hyper Text Transfer Protocol&#xff09;&#xff0c;简称HTTP&#xff0c;是一种基于…

LwIP应用开发笔记之八:LwIP无操作系统HTTP客户端

前面我们实现了TCP服务器和客户端的简单应用&#xff0c;接下来我们实现一个基于TCP协议的应用协议&#xff0c;那就是HTTP超文本传输协议 1、HTTP协议简介 超文本传输协议&#xff08;Hyper Text Transfer Protocol&#xff09;&#xff0c;简称HTTP&#xff0c;是一种基于T…

LwIP应用开发笔记之九:LwIP无操作系统TELNET服务器

前面我们已经实现了基于RAW API的TCP服务器和客户端&#xff0c;也在此基础上实现了HTTP应用。接下来我们实现一个基于TCP的Telnet服务器应用。 1、Telnet协议简介 Telnet协议是TCP/IP协议族中的一员&#xff0c;是Internet远程登陆服务的标准协议和主要方式。它为用户提供了…

在ARM Cortex-M上实现FreeRTOS性能计数器

说明&#xff1a;本文翻译自Erich Styger的文章《Implementing FreeRTOS Performance Counters on ARM Cortex-M》&#xff0c;文章的权属属于原作者。 当使用像FreeRTOS这样的RTOS时&#xff0c;迟早要问一个问题&#xff1a;每个任务花费多少时间&#xff1f;基于Eclipse的M…

STM32学习及开发笔记八:采用主从计时器实现精确脉冲输出

脉冲信号用于设备控制是非常常见的&#xff0c;但在一些情况下&#xff0c;我们希望精确的控制脉冲的数量以实现对运动的精确控制。实现的方式也许有多种多样&#xff0c;但使用计时器来实现此类操作是人们比较容易想到的。 1、原理概述 我们知道在STM32平台上&#xff0c;使…

外设驱动库开发笔记0:EPD总体设计

在产品开发过程中&#xff0c;不可避免需要使用很多外部的元件及传感器&#xff0c;这些元器件也许是板载的&#xff0c;也许是板外的&#xff0c;但不管怎样&#xff0c;为其开发驱动程序都是必须的。每次都需要为这些元器件编写驱动程序。但每次重复编写调试很麻烦&#xff0…

外设驱动库开发笔记1:AD56xx系列DAC驱动

DAC在我们的项目中经常使用到&#xff0c;而使用最多的就是AD56xx系列&#xff0c;包括有单通道的AD5662、双通道的AD5623和AD5663、以及四通道的AD5624和AD5664等。出于方便复用的原因&#xff0c;我们设计并实现AD56xx系列DAC的驱动。 1、功能概述 AD56xx系列DAC属于nanoDA…

外设驱动库开发笔记2:AD8400系列数字电位器驱动

一些时候我们需要在系统使用过程中改变某些电路电阻值以达到改变设定的目的&#xff0c;这时候我们就会使用电位器。在我们使用数字控制电路时多选择数字电位器。在这一篇我们就来设计AD8400系列数字电位器的驱动。 1、功能概述 AD8400/AD8402/AD8403分别是单通道/双通道/四通…

外设驱动库开发笔记3:AD527x系列数字电位器驱动

在一些时候我们需要使用精度更高的数字电位器来实现我们的应用。我们经常使用AD527x系列数字电位器来实现这类应用。在通常情况下&#xff0c;AD527x系列数字电位器完全能够满足要求。为了减少重复工作&#xff0c;在这里我们将分系并实现AD527x系列数字电位器的驱动。 1、功能…

PID控制器改进笔记之一:改进PID控制器之参数动态调整

前面我们发布了一系列PID控制器相关的文章&#xff0c;包括经典PID控制器以及参数自适应的PID控制器。这一系列PID控制器虽说实现了主要功能&#xff0c;也在实际使用中取得了良好效果&#xff0c;但还有很多的细节部分可以改进以提高性能和灵活性。所以在这篇中我们来讨论改进…

外设驱动库开发笔记4:AD9833函数发生器驱动

很多时候我们需要输出某种函数信号&#xff0c;如方波、三角波、正弦波等&#xff0c;但想要获得这样的函数信号&#xff0c;不论是硬件电路还是软件实现&#xff0c;却并不是一件简单的事情。不过AD9833这类函数生成芯片可以简化这方面的操作&#xff0c;这一节我们就来设计并…