完善资料让更多小伙伴认识你,还能领取20积分哦, 立即完善>
扫一扫,分享给好友
|
|
相关推荐
1个回答
|
|
演示视频
【Arduino 101】五分钟搞懂PID控制算法 物料清单 Arduino Uno x 1 超声波模块(HC-SR04)x 1 舵机(Tower Pro MG996R)x 1 舵机供电: 5V 稳压管(LM7805) x 1 , 滤波电容 (0.33uF, 0.1uF) x 2, 9V 电池 x 1 滑轨:泡沫板 支架:乐高 滚动物体:胶带(Up试过网球,但是测距模块的表现不理想) 尺寸 & 设计缺陷 设计缺陷: 1: 测距模块读数不稳定,存在+/-5mm 的浮动。 2: 整体制作比较粗糙,轨道摩擦不均匀。对稳态误差的出现原因仅仅是个猜测,所以视频中用了“可能”两个字。 接线 Arduino IDE 代码 /* PID control Demo, PID 控制算法演示 * Last Edited: March.12th.2021 by Mun Kim * Contact: Robotix.Kim@gmail.com */ #include Servo servo; int angle = 0; //舵机角度 #define echo 2 //HC-SR04的Echo接 Arduino D2 #define trig 3 //HC-SR04的Trig接 Arduino D3 float time, duration, distance; //PID constants**************************************************************** float setPoint=19; //滑轨中心与测距模块的距离 float error; //当前误差 float previous_error; //上一时刻误差,用来计算D float kp=0; //10 float ki=0; //0.05 float kd=0; //200 int dt=50; //每50毫秒进行一次计算 float P,I,D, PID; //***************************************************************************** void setup() { Serial.begin(9600); pinMode(trig, OUTPUT); pinMode(echo, INPUT); servo.attach(9); time = millis(); } void loop() { if (millis() > time + dt) { time = millis(); // HC-SR04 Distance Measuremnt, 通过超声波模块测量胶带的位置******************* digitalWrite(trig, LOW); delayMicroseconds(2); digitalWrite(trig, HIGH); delayMicroseconds(10); digitalWrite(trig, LOW); duration = pulseIn(echo, HIGH); //读取反射信号 distance = (duration*0.0343)/2; //测距公式,单位为cm // PID Calculation, PID计算************************************************* error = distance-setPoint; //计算误差 P = kp*error; //P项 if(-4 < error && error < 4){ I += ki*error; } //I项 else{ I = 0; } D = kd*((error - previous_error)/dt); //D项, PID=P + I + D ; //PID if (PID>200){PID=200;} //限幅 if (PID<-200){PID=-200;} //限幅 previous_error=error; //更新上一时刻误差 // Serial Display,在串口监视器显示每个项,有助于调试***************************** Serial.print("Distance: "); Serial.print(distance); Serial.print(" cm "); Serial.print("Error: "); Serial.print(error); Serial.print(" cm "); Serial.print(" P: "); Serial.print(P); Serial.print(" D: "); Serial.print(D); Serial.print(" I: "); Serial.print(I); Serial.print(" PID: "); Serial.println(PID); // Servo Control,用计算结果控制舵机******************************************* angle = map(PID, -200,200,150,20); servo.write(angle); } } |
|
|
|
只有小组成员才能发言,加入小组>>
2371 浏览 0 评论
8683 浏览 4 评论
36409 浏览 18 评论
4967 浏览 0 评论
24179 浏览 34 评论
1336浏览 2评论
1585浏览 1评论
1953浏览 1评论
1399浏览 0评论
1834浏览 0评论
小黑屋| 手机版| Archiver| 电子发烧友 ( 湘ICP备2023018690号 )
GMT+8, 2024-11-10 16:19 , Processed in 0.979874 second(s), Total 46, Slave 40 queries .
Powered by 电子发烧友网
© 2015 bbs.elecfans.com
关注我们的微信
下载发烧友APP
电子发烧友观察
版权所有 © 湖南华秋数字科技有限公司
电子发烧友 (电路图) 湘公网安备 43011202000918 号 电信与信息服务业务经营许可证:合字B2-20210191 工商网监 湘ICP备2023018690号