pid算法(经典)

上传人:子 文档编号:43336866 上传时间:2018-06-05 格式:DOC 页数:19 大小:22.96KB
返回 下载 相关 举报
pid算法(经典)_第1页
第1页 / 共19页
pid算法(经典)_第2页
第2页 / 共19页
pid算法(经典)_第3页
第3页 / 共19页
pid算法(经典)_第4页
第4页 / 共19页
pid算法(经典)_第5页
第5页 / 共19页
点击查看更多>>
资源描述

《pid算法(经典)》由会员分享,可在线阅读,更多相关《pid算法(经典)(19页珍藏版)》请在金锄头文库上搜索。

1、PIDPID 算法算法( (经典经典) )小明接到这样一个任务:有一个水缸点漏水(而且漏水的速度还不一定固定不变),要求水面高度维持在某个位置,一旦发现水面高度低于要求位置,就要往水缸里加水。 小明接到任务后就一直守在水缸旁边,时间长就觉得无聊,就跑到房里看小说了,每 30 分钟来检查一次水面高度。水漏得太快,每次小明来检查时,水都快漏完了,离要求的高度相差很远,小明改为每 3 分钟来检查一次,结果每次来水都没怎么漏,不需要加水,来得太频繁做的是无用功。几次试验后,确定每 10 分钟来检查一次。这个检查时间就称为 (采样周期)。 开始小明用瓢加水,水龙头离水缸有十几米的距离,经常要跑好几趟才加

2、够水,于是小明又改为用桶加,一加就是一桶,跑的次数少了,加水的速度也快了,但好几次将缸给加溢出了,不小心弄湿了几次鞋,小明又动脑筋,我不用瓢也不用桶,老子用盆,几次下来,发现刚刚好,不用跑太多次,也不会让水溢出。这个加水工具的大小就称为 (比例系数。) 小明又发现水虽然不会加过量溢出了,有时会高过要求位置比较多,还是有打湿鞋的危险。他又想了个办法,在水缸上装一个漏斗,每次加水不直接倒进水缸,而是倒进漏斗让它慢慢加。这样溢出的问题解决了,但加水的速度又慢了,有时还赶不上漏水的速度。于是他试着变换不同大小口径的漏斗来控制加水的速度,最后终于找到了满意的漏斗。漏斗的时间就称为积分时间 。小明终于喘了

3、一口,但任务的要求突然严了,水位控制的及时性要求大大提高,一旦水位过低,必须立即将水加到要求位置,而且不能高出太多,否则不给工钱。小明又为难了!于是他又开努脑筋,终于让它想到一个办法,常放一盆备用水在旁边,一发现水位低了,不经过漏斗就是一盆水下去,这样及时性是保证了,但水位有时会高多了。他又在要求水面位置上面一点将水凿一孔,再接一根管子到下面的备用桶里这样多出的水会从上面的孔里漏出来。这个水漏出的快慢就称为微分时间。大学时代做机器人时用的 PID 算法源代码:#define PID_Uint struct pid_uintPID_Uintint U_kk;int ekk;int ekkk;in

4、t Ur; /限幅输出值,需初始化int Un; /不灵敏区/int multiple; /PID 系数的放大倍数,用整形数据的情况下,提高 PID 参数的设置精度 固定为 256int Kp; /比例,从小往大调int Ti; /积分,从大往小调int Td; /微分,用巡线板时设为 0int k1; /int k2;int k3;/* 函 数 名:void Init_PID_uint(PID_uint *p)功 能:初始化 PID 参数说 明:调用本函数之前,应该先对 Kp,Ti,Td 做设置 ,简化了公式入口参数:PID 单元的参数结构体 地址返 回 值:无*/void Init_PID

5、_uint(PID_Uint *p)p-k1=(p-Kp)+(p-Kp)*1024/(p-Ti)+(p-Kp)*(p-Td)/1024;p-k2=(p-Kp)+2*(p-Kp)*(p-Td)/1024;p-k3=(p-Kp)*(p-Td)/1024;/* 函 数 名:void reset_Uk(PID_Uint *p)功 能:初始化 U_kk,ekk,ekkk说 明:在初始化时调用,改变 PID 参数时有可能需要调用入口参数:PID 单元的参数结构体 地址返 回 值:无*/void reset_Uk(PID_Uint *p)p-U_kk=0;p-ekk=0;p-ekkk=0;/* 函 数 名:

6、int PID_commen(int set,int jiance,PID_Uint *p)功 能:通用 PID 函数说 明:求任意单个 PID 的控制量入口参数:期望值,实测值,PID 单元结构体返 回 值:PID 控制量*/int PID_common(int set,int jiance,PID_Uint *p)int ek,U_k=0;ek=jiance-set;if(ek(p-Un)|(ekUn) /积分不灵敏区U_k=(p-U_kk)+(p-k1)*ek-(p-k2)*(p-ekk)+(p-k3)*(p-ekkk);p-U_kk=U_k;p-ekkk=p-ekk;p-ekk=ek;

7、if(U_k(p-Ur) /限制最大输出量,U_k=p-Ur;if(U_kUr)U_k=-(p-Ur); return U_k/1024; /*=*/typedef struct PID / signed int vi_Ref; / 设置的速度 这两个参数由于是动态变化的所以。 。 。/ signed int vi_FeedBack; / 传感器读回来的速度 用形式参数long int vi_PreError; / E-1 errorlong int vi_PreDerror; / E-2 errorunsigned int v_Kp; / Punsigned int v_Ki; / I th

8、ree parameterunsigned int v_Kd; / Dlong int vl_PreU; /所得电压PID;PID sPID12;PID *pp1 =PID *pp2 = / PID Control Structurelong int v_PIDCalc1( signed short set_point,signed short next_point)signed long error,d_error,dd_error; error = (signed long)(set_point - next_point); d_error = error - pp1-vi_PreErro

9、r;dd_error = d_error - pp1-vi_PreDerror;pp1-vi_PreError = error; pp1-vi_PreDerror = d_error;if( ( error -VV_DEADLINE ) ); else pp1-vl_PreU +=(signed long)( pp1 - v_Kp * d_error + pp1 - v_Ki * error + pp1-v_Kd*dd_error);if( pp1-vl_PreU = VV_MAX ) pp1-vl_PreU = VV_MAX;else if( pp1-vl_PreU vl_PreU = 0;

10、 else if(error20)pp1-vl_PreU=VV_MAX; return (pp1-vl_PreU); long int v_PIDCalc2( signed short set_point,signed short next_point)signed long error,d_error,dd_error; error = (signed long)(set_point - next_point); d_error = error - pp2-vi_PreError;dd_error = d_error - pp2-vi_PreDerror;pp2-vi_PreError =

11、error; pp2-vi_PreDerror = d_error;if( ( error -VV_DEADLINE ) ); else pp2-vl_PreU +=(signed long)( pp2 - v_Kp * d_error + pp2 - v_Ki * error + pp2-v_Kd*dd_error);if( pp2-vl_PreU = VV_MAX ) pp2-vl_PreU = VV_MAX;else if( pp2-vl_PreU vl_PreU = 0; else if(error20)pp2-vl_PreU=VV_MAX; return (pp2-vl_PreU); void PIDInit () / sPID1.vi_Ref = 0 ; / sPID1.vi_FeedBack = 0 ; pp1-vi_PreError = 0 ; pp1-vi_PreDerror = 0 ; pp1-v_Kp = VV_KPVALUE;pp1-v_Ki = VV_KIVALUE;pp1-v_Kd = VV_KDVA

展开阅读全文
相关资源
相关搜索

当前位置:首页 > 生活休闲 > 科普知识

电脑版 |金锄头文库版权所有
经营许可证:蜀ICP备13022795号 | 川公网安备 51140202000112号