精华内容
下载资源
问答
  • 智能车PID 控制

    万次阅读 2018-09-01 03:53:09
    PID 控制策略其结构简单, 稳定性好, 可靠性高, 并且易于实现。 其缺点在于控制器的参数整定相当繁琐, 需要很强的工程经验。 相对于其他的控制方式,在成熟性和可操作性上都有着很大的优势。 使用试凑法来确定...

    PID 控制策略其结构简单, 稳定性好, 可靠性高, 并且易于实现。 其缺点在于控制器的参数整定相当繁琐, 需要很强的工程经验。 相对于其他的控制方式,在成熟性和可操作性上都有着很大的优势。 使用试凑法来确定控制器的比例、 积分和微分参数。
    试凑法是通过闭环试验, 观察系统响应曲线, 根据各控制参数对系统响应的大致影响, 反复试凑参数, 以达到满意的响应, 最后确定 PID 控制参数。 试凑不是盲目的,而是在控制理论指导下进行的。在控制理论中已获得如下定性知识:

    比例调节(P)作用:
    是按比例反应系统的偏差, 系统一旦出现了偏差, 比例调节立即产生调节作用用以减少偏差。 比例作用大, 可以加快调节, 减少误差, 但是过大的比例,使系统的稳定性下降, 甚至造成系统的不稳定。
    积分调节(I) 作用:
    是使系统消除稳态误差, 提高无差度。 因为有误差, 积分调节就进行, 直至无差, 积分调节停止, 积分调节输出一常值。 积分作用的强弱取决与积分时间常数 Ti, Ti 越小, 积分作用就越强。 反之 Ti 大则积分作用弱, 加入积分调节可使系统稳定性
    下降, 动态响应变慢。 积分作用常与另两种调节规律结合, 组成 PI 调节器或 PID调节器。

    微分调节(D) 作用:
    微分作用反映系统偏差信号的变化率, 具有预见性, 能预见偏差变化的趋势, 因此能产生超前的控制作用, 在偏差还没有形成之前, 已被微分调节作用消除。 因此, 可以改善系统的动态性能。 在微分时间选择合适情况下, 可以减少超调, 减少调节时间。 微分作用对噪声干扰有放大作用,因此过强的加微分调节, 对系统抗干扰不利。 此外, 微分反应的是变化率, 而当输入没有变化时, 微分作用输出为零。 微分作用不能单独使用, 需要与另外两种调节规律相结合, 组成 PD 或 PID 控制器。

    舵机pd控制

    舵机控制
    其关键部分代码如下:
    servo_pwm_change = (wucha_Now* Kp_servo + Kd_servo*(wucha_Now-wucha_Last)) / 100;
    其中, KP_servoKD_servo 两个重要的参数需要经过不断调整。 在实际调试中发现, 针对赛道类型给定参数更符合实际。 例如, 在直道和小 S 路上相应的KP_servo 可以给小, 以防舵机打角过大。 分段各段之间参数的给定要连续, 否
    则会出现舵机在参数切换之后出现较大突变, 导致智能汽车的路径变差。 我们设置一个数学函数控制参数的输出, 减少调节参数的工作量。 当然为了防止把舵机的齿轮打坏, 应该对舵机的打角进行限幅处理。

    展开全文
  • 基于DG128的PID控制程序,已在code warrior中编译过了!
  • 51单片机智能小车PID速度控制算法源代码,该PID算法可以将智能小车的速度控制在设定的速度值上。需要结合测速模块使用。
  • pid控制器设计代码matlab SmartCarSpeedControl-PI 智能车速度PI控制器 飞思卡尔智能车比赛Matlab仿真速度控制PI的模型 Matlab R2011a 在Matlab下,打开SpeedControl.mdl,运行即可,点击Scope查看仿真结果 C程序部分...
  • 基于K60芯片智能车控制代码 开机后,对所有硬件进行初始化,完成之后,PIT 定时中断,对电感采回来的数值进行分析,根据比例关系算出赛道电流大小并自动设置对应该电流时 最佳参数。正式起跑后定时的采集感应电压。...
  • 包含很多模糊控制的文档,介绍了模糊控制基本原理与实现步骤以及在智能小车中的应用,可用模糊控制调节PID参数
  • 两轮智能车PID控制如何实现

    千次阅读 2020-01-03 15:52:39
    都知道PID控制,但是总是没有搞清楚,看了很多公式和图形就是没整明白。下面这个图形就是pid控制的原理图。 PID算法在很多方面都有重要应用,比如电机的速度控制,恒温槽的温度控制,四轴飞行器的平衡控制等等,...

    PID基础理论知识

    都知道PID控制,但是总是没有搞清楚,看了很多公式和图形就是没整明白。下面这个图形就是pid控制的原理图。

    PID算法在很多方面都有重要应用,比如电机的速度控制,恒温槽的温度控制,四轴飞行器的平衡控制等等,作为闭环控制系统中的一种重要算法,PID算法是有比例,积分,微分三部分组成。关于PID通俗易懂的一篇文章介绍,推荐博客网址:https://blog.csdn.net/qq_25352981/article/details/81007075

    比例部分

                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控制技术

    我做的智能车主要是两轮,那就介绍两轮的PID控制方法,多轮可以照样改写。把之前制作的遥控收球机的代码放到这里跟大家分享。

    对于两轮智能车的PID控制主要使用了下面这个函数:

    
    void bieber_moto_Control(float current_speed,float target_speed, unsigned char Moto_ID)
    {
    	float Error   = 0;
    	float P_Error = 0;
    	float I_Error = 0;
    	float D_Error = 0;
    	float add     = 0;
    	
    	if(Moto_ID == LEFT)
    	
    		Error = target_speed - current_speed;                  //计算误差
    		P_Error = Error;                                       //比例环节
    		I_Error = Error - Left_L_Error;                        //积分环节
    		D_Error = Error - 2*Left_L_Error + Left_LL_Error;      //微分环节
    		
    		add = KP * P_Error + KI * I_Error + KD * D_Error;      //左轮PID增加值
    		Left_ESC_Output_PWM += add;                            //计算PWM输出值
    		
    		Left_LL_Error = Left_L_Error;
    		Left_L_Error = Error;
    		
    	
    	else if(Moto_ID == RIGHT)
    	{
    		Error = target_speed - current_speed;                   //计算误差
    		P_Error = Error;                                        //比例环节
    		I_Error = Error - Right_L_Error;                        //积分环节
    		D_Error = Error - 2*Right_L_Error + Right_LL_Error;     //微分环节
    
    		add = KP * P_Error + KI * I_Error + KD * D_Error;       //左轮PID增加值
    		Right_ESC_Output_PWM += add;                            //计算PWM输出值
    		
    		Right_LL_Error = Right_L_Error;
    		Right_L_Error = Error;
    	}
    
    	PWM_Output(Left_ESC_Output_PWM, Right_ESC_Output_PWM);  //输出左右轮的PWM
    }
    

     希望上面代码对你开发两轮智能车有一定帮助,谢谢大家!

    展开全文
  • 今天我代表历届参加大赛的网友,给大家分享一些有关PID的学习代码pid算法和研究、PID智能车黑线识别算法及控制策略研究、PID电机调速等等。需要参加智能车大赛的朋友,赶紧充电学习下 PID算法吧。 智能车大赛PID...
  • 智能车舵机控制PID

    热门讨论 2012-11-20 01:33:10
    增量式pid控制的可以看看运用在智能车的舵机 分享给大家,欢迎交流啊
  • 使用Linux系统,ros机器人操作系统,gazebo仿真软件,利用rospy等python包所带工具进行智能小车运动仿真.在给定的地图当中跑完一圈,1分钟之内为满分.现将笔者所编写之代码与小伙伴们分享,希望能够抛砖引玉.本文只做参考...

    使用Linux系统,ros机器人操作系统,gazebo仿真软件,利用rospy等python包所带工具进行智能小车运动仿真.在给定的地图当中跑完一圈,1分钟之内为满分.现将笔者所编写之代码与小伙伴们分享,希望能够抛砖引玉.本文只做参考,切忌全部代码照抄哦~
    该代码最终验收成绩为54-55秒之间.视虚拟机内存,电脑电量等,性能会有一定波动.建议虚拟机内存拉到14G以上(笔者验收时的配置)
    PID调试方法:先调P,逐渐增大直至出现震荡;再调D,在保证转弯不耗费太多时间的情况下不损失太多速度.微分控制可以预见error的变化,从而使得调节过程更加平稳顺滑,表现出来就是过弯过的稳.积分控制一般用来减小稳态误差,这里不使用积分控制.说起来容易做起来难,涉及到的其他参数还是比较多,而且参数之间强耦合,牵一发动全身,需要大量时间.将代码分享出来,也是为了小伙伴们调参的时候可以舒服一点.

    #!/usr/bin/env python
    # BEGIN ALL
    import rospy, cv2, cv_bridge, numpy, time
    from sensor_msgs.msg import Image
    from geometry_msgs.msg import Twist
    
    class PID:
        def __init__(self, P, I, D):
            self.Kp = P
            self.Ki = I
            self.Kd = D
            self.current_time = time.time()  #用来计算时间差,留作微分控制用
            self.last_time = self.current_time
            self.PTerm = 0.0
            self.ITerm = 0.0
            self.DTerm = 0.0
            self.last_error = 0.0 #上次的误差,留作微分控制用
            self.output = 0.0 #PID控制器输出
            self.bridge = cv_bridge.CvBridge()
            self.image_sub = rospy.Subscriber('camera/image_raw', Image, self.image_callback)
            self.cmd_vel_pub = rospy.Publisher('/cmd_vel', Twist, queue_size=1)
            self.twist = Twist()
    
        def image_callback(self, msg):  #主要函数,该函数的调用次数与性能与电脑状况(如电量,虚拟机内存等严重相关)
            image = self.bridge.imgmsg_to_cv2(msg, desired_encoding='bgr8')
            hsv = cv2.cvtColor(image, cv2.COLOR_BGR2HSV)
            lower_white = numpy.array([0, 0, 221])
            upper_white = numpy.array([180, 30, 255])
            mask = cv2.inRange(hsv, lower_white, upper_white) #将摄像头看到的图像做二值化处理
            mask1 = mask.copy()
            mask2 = mask.copy()
    
            h, w, d = image.shape
            search_top1 = 3 * h / 4 + 20
            search_bot1 = 3 * h / 4 + 40
            mask1[0:search_top1, 0:w] = 0
            mask1[search_bot1:h, 0:w] = 0
            M1 = cv2.moments(mask1)
            search_top2 = 3 * h / 4 - 70
            search_bot2 = 3 * h / 4 - 50
            mask2[0:search_top2, 0:w] = 0
            mask2[search_bot2:h, 0:w] = 0
            M2 = cv2.moments(mask2) #计算两张二值化图片的矩
    
            if (M1['m00'] > 0):
                cx1 = int(M1['m10'] / M1['m00'])
                cy1 = int(M1['m01'] / M1['m00'])
                cv2.circle(image, (cx1, cy1), 20, (0, 0, 255), -1)
                if (M2['m00'] > 0):
                    cx2 = int(M2['m10'] / M2['m00'])
                    cy2 = int(M2['m01'] / M2['m00'])
                    cv2.circle(image, (cx2, cy2), 20, (0, 0, 255), -1) #将两个重心点在图像中
                    err = cx1 * 0.55 + cx2 * 0.45  - w / 2  #误差函数设计,原始加权为0.5 0.5,可进行微调,改进效果并不明显
                    self.current_time = time.time() #不要忘记时间的处理,微分控制的关键
                    delta_time = self.current_time - self.last_time #计算时间差
                    self.PTerm = self.Kp * err
                    self.DTerm = (err - self.last_error) * self.Kd  #参考位置式PID公式即可
                    self.output = self.PTerm + self.ITerm + self.DTerm #计算PID控制器输出
                    output = self.output
                    self.twist.linear.x = -2.2 * (1 - abs(err) / 770) #线速度,err的一次函数
                    self.twist.angular.z = float(self.output) / 45 #角速度,使用PID控制器,主要目的在于使小车转弯平滑且不明显减速
                    self.cmd_vel_pub.publish(self.twist)
                    self.last_error = err # 将这次的err赋给last_error
                    cv2.imshow("mask", mask) #输出二值化图像
                    cv2.waitKey(3)
    
    
    P = 2
    I = 0
    D = 6
    rospy.init_node('follower')
    follower = PID(P, I, D)
    rospy.spin()
    
    

    这里并没有将PID控制器的输出直接赋给角速度,而是除以了一个分母(原始代码是除以50),这样再调PID时可以只挑整数,体验好一些.
    关于误差函数:原始代码只取了一个点.这里取了两个点,也可以取三个甚至更多的点,甚至使用非线性的组合,但粗略尝试之后发现性能不增反减,故作罢.但相比一点式,提升十分明显.
    希望可以帮到大家!

    展开全文
  • 算法(一):智能小车速度控制PID模糊控制

    万次阅读 多人点赞 2020-03-22 10:42:36
    概览一、前言二、基于PID 的速度控制1.PID控制器2.PID速度控制二、基于模糊控制的速度控制1....在实现智能小车速度的闭环控制时首选简单有效的PID控制算法。 二、基于PID 的速度控制 1.PID控制器 PID(Proportion I...

    一、前言

    本科的时候参加飞思卡尔比赛,在队友的神助攻下有幸拿了国奖,比赛中使用了模糊控制算法。这段时间正好看到了模糊控制算法,就把以前的代码翻出来,顺便总结一下PID和模糊控制算法,希望自己能养成记录知识点的好习惯。

    二、基于PID 的速度控制

    在控制领域,PID算法是应用最广泛的算法之一。小到电机的转速,大到机器人稳定性的控制。在实现智能小车速度的闭环控制时首选简单有效的PID控制算法。

    1.PID控制器

    PID(Proportion Integration Differentiation)控制器包括P比例、I积分和D微分三个控制单元,协同工作保证控制系统快速到达并稳定于目标值。PID控制算法的公式:
    u(t)=Kperr(t)+Kierr(t)dt+Kdderr(t)dtu(t)=K_perr(t)+K_i\int err(t)dt +K_d\frac{derr(t)}{dt}
    对其进行离散化:
    u(n)=Kperr(n)+Kik=0nerr(k)+Kd(err(n)err(n1))u(n)=K_perr(n)+K_i\sum_{k=0}^n err(k) +K_d(err(n)-err(n-1))

    1)KpK_p比例控制
    控制器的反应速度与KpK_p有关,该系数越大,控制系统反应更灵敏。但是KpK_p过大会引起较大的超调,并产生震荡,破坏系统的稳定性。因此在调整KpK_p参数时应从低到高增加,选择系统达到响应快并稳定的效果时的参数。

    2)KiK_i积分控制
    只要控制系统存在误差,该系数对系统的作用就会不断增强。只有误差err消失即系统稳定在目标值时,控制作用才不会变化。由此可见积分控制的调节会消除系统的静态误差。

    3)KdK_d微分控制
    为了抑制系统的超调和振荡,在控制系统中增加微分控制。通过对控制系统未来的预估,及时对控制量进行调整,提升系统的稳定性。

    2.PID速度控制

    刚开始对小车的速度控制采用位置式PID控制算法,即常用的PID控制算法。但是位置式PID算法使用过去误差的累加值,容易产生较大的累计误差。而且由于小车的目标速度时刻在变化,err值需要不断的累加,可能出现err_sum溢出的情况。因此对位置式加以变换,得到增量式PID控制算法:
    u=u(n)u(n1)=Kp(err(n)err(n1))+Kierr(n)+Kd(err(n)2err(n1)+err(n2))\triangle u=u(n)-u(n-1)=K_p(err(n)-err(n-1))+K_ierr(n) +K_d(err(n)-2err(n-1)+err(n-2))
    由此计算出:
    u(n)=u(n1)+Kp(err(n)err(n1))+Kierr(n)+Kd(err(n)2err(n1)+err(n2)) u(n) = u(n-1) + K_p(err(n)-err(n-1))+K_ierr(n) +K_d(err(n)-2err(n-1)+err(n-2))

    int speed_control(void)
    {
    	int i;
    	speed_set=get_speed_set();//设置车速                  
    	
    	//设置PID参数
    	kp_motor=33;
    	ki_motor=0.038;
    	kd_motor=0.04;
    
    	for(i=0;i<9;i++)
    		error[i]=error[i+1];
    	error[9]=speed_set-speed;	
    
    	de=kp_motor*(error[9]-error[8])+ki_motor*error[9]-kd_motor*(speed_save[9]-2*speed_save[8]+speed_save[7]);
    	pwm1 = pwm1_old+de;
      	
      	speed_set_old=speed_set;
      	pwm1_old=pwm1; 
      	return pwm1;//输出PWM波
    }
    

    二、基于模糊控制的速度控制

    拥有响应迅速地速度控制系统对于提升小车的速度是不够的,还需要根据赛道情况设置不同的车速以实现小车最快地通过不同的路况。这时,可以考虑模糊控制的思想根据路况及小车当前的状态对目标车速进行设置。

    1.变量的模糊化

    在模糊控制中,输入输出变量大小用语言形式进行描述。常选用的7个语言值为{负大,负中,负小,零,正小,正中,正大},即{NB,NM,NS,O,PS,PM,PB}。

    对小车当前行驶方向和赛道方向形成的偏差e及其变化率ec作为模糊控制器的输入,小车的目标车速为模糊控制器的输出。设偏差值的模糊量为E,偏差变化率模糊量为EC,U为目标车速。为了让速度切换更加细腻流畅,设置偏差e、偏差变化ec和控制量u的基本论域为[-6,6],并划分为13个等级,即{-6,-5,-4,-3,-2,-1,0,1,2,3,4,5,6}。

    E、EC和U均使用三角形隶属函数进行模糊化

    三角形隶属函数

    
    /**
    * 列坐标:NB,NM,NS,O,PS,PM,PB
    * 横坐标:-6,-5,-4,-3,-2,-1,0,1,2,3,4,5,6
    * @param 建立输入、输出隶属度函数,进行微调调整模糊量的范围
    */
    /***************************************误差隶属度函数***************************************/
    float Input1_Terms_Membership[7][13] =
    { 1,0.15,0,0,0,0,0,0,0,0,0,0,0,
    0,0.2,1,0.2,0,0,0,0,0,0,0,0,0,
    0,0,0,0.2,1,0.2,0,0,0,0,0,0,0,
    0,0,0,0,0,0.1,1,0.1,0,0,0,0,0,
    0,0,0,0,0,0,0,0.1,1,0.1,0,0,0,
    0,0,0,0,0,0,0,0,0,0.2,1,0.2,0,
    0,0,0,0,0,0,0,0,0,0,0,0.2,1
    };
    /***************************************误差变化率隶属度函数***************************************/
    float Input2_Terms_Membership[7][13] =
    { 1,0.15,0,0,0,0,0,0,0,0,0,0,0,
    0,0.2,1,0.2,0,0,0,0,0,0,0,0,0,
    0,0,0,0.2,1,0.2,0,0,0,0,0,0,0,
    0,0,0,0,0,0.1,1,0.1,0,0,0,0,0,
    0,0,0,0,0,0,0,0.1,1,0.1,0,0,0,
    0,0,0,0,0,0,0,0,0,0.2,1,0.2,0,
    0,0,0,0,0,0,0,0,0,0,0,0.2,1
    };
    /***************************************输出(速度)***************************************/
    float Output_Terms_Membership[7][13] =
    { 1,0.15,0,0,0,0,0,0,0,0,0,0,0,
    0,0.2,1,0.2,0,0,0,0,0,0,0,0,0,
    0,0,0,0.2,1,0.2,0,0,0,0,0,0,0,
    0,0,0,0,0,0.1,1,0.1,0,0,0,0,0,
    0,0,0,0,0,0,0,0.1,1,0.1,0,0,0,
    0,0,0,0,0,0,0,0,0,0.2,1,0.2,0,
    0,0,0,0,0,0,0,0,0,0,0,0.2,1
    };
    

    2.模糊查询表的计算

    对模糊量EC、E和U设置相关的模糊控制规则表
    模糊控制规则表

    /**
    * 纵轴为E(error),横轴为EC(error_delta),值为速度七档NB(0),NM(1),NS(2),Z(3),PS(4),PM(5),PB(6)速度由小变大再变小
    * 列坐标:E(NB,NM,NS,O,PS,PM,PB)
    * 横坐标:EC(NB,NM,NS,O,PS,PM,PB)
    * 值:U(1:NB:2,NM,3:NS,4:O,5:PS,6:PM,7:PB)
    * @param 模糊控制规则表,调整速度变化趋势
    */
    int Rule[7][7] =
    { 1,1,2,2,6,7,7,
     1,1,2,2,6,6,6,
     1,2,3,4,5,6,6,
     1,3,4,4,4,5,7,
     2,2,3,4,5,6,7,
     2,2,2,2,6,7,7,
     1,1,2,2,6,7,7
    };//调试参数
    

    规则库蕴含的模糊关系:

    R=(E×EC)×CR=(E\times EC)\times C

    其中,模糊运算×\times表示“取小”。

    计算出模糊规则蕴含的模糊关系R后,通过遍历E和EC所有的论域对模糊值进行选取并计算模糊输出值:

    U=(E×EC)RU^*=(E^* \times EC^*)\circ R

    其中,\circ表示模糊矩阵的合成,类似于普通矩阵的乘积运算,将乘积运算换成“取小”,将加法运算换成“取大”。

    在遍历过程中,对E和EC所有论域对应的模糊输出值一一采取加权平均法去模糊化,得到最终的模糊控制器查询表。

    float  R[169][13] = { 0 };
    float R1[13][13] = { 0 };
    float AdBd1[13][13] = { 0 };
    float R2[169] = { 0 };
    float AdBd2[169] = { 0 };
    float R3[169][13] = { 0 };
    float  Cd[13] = { 0 };
    float Fuzzy_Table[13][13] = { 0 };
    float SPEED[13] = { 200,220,230,240,250,270,300,270,250,240,230,220,200 };//调试参数
    int Max_Input1_value = 0, Max_Input2_value = 0;
    
    /**
    * @param 模糊化过程实现论域内不同值对应隶属度最大的语言值
    */
    int  E_MAX(int e)
    {
    	int i = 0, max = 0;
    	for (i = 0; i < 7; i++)
    		if (Input1_Terms_Membership[i][e] > Input1_Terms_Membership[max][e])
    			max = i;
    	return max;
    }
    
    int  EC_MAX(int ex)
    {
    	int i = 0, max = 0;
    	for (i = 0; i < 7; i++)
    		if (Input2_Terms_Membership[i][ex] > Input1_Terms_Membership[max][ex])
    			max = i;
    	return max;
    }
    
    void calculate()
    {
    	/***************************************计算所有规则模糊关系的并集Rule***************************************/
    	int i = 0, j = 0, k = 0;
    	int Input1_value_index = 0, Input2_value_index = 0;
    
    	//计算Rule(初始化),计算Rij,并对所有的R取并集,R=(EXEC)XU
    	for (Input1_Terms_Index = 0; Input1_Terms_Index < 7; Input1_Terms_Index++)
    		for (Input2_Terms_Index = 0; Input2_Terms_Index < 7; Input2_Terms_Index++)
    		{
    			// E和EC的语言值两两组合及其输出计算Rule
    			Output_Terms_Index = Rule[Input1_Terms_Index][Input2_Terms_Index] - 1;
    			k = 0;
    			for (i = 0; i < 13; i++)
    				for (j = 0; j < 13; j++)
    				{
    					// E和EC进行取小运算
    					if (Input1_Terms_Membership[Input1_Terms_Index][i] < Input2_Terms_Membership[Input2_Terms_Index][j])
    						R1[i][j] = Input1_Terms_Membership[Input1_Terms_Index][i];
    					else
    						R1[i][j] = Input2_Terms_Membership[Input2_Terms_Index][j];
    					// 转换R1矩阵为R2一维向量
    					R2[k] = R1[i][j];
    					k++;
    				}
    			///<A=Input1_Terms_Membership[Input1_Terms_Index],B=Input2_Terms_Membership[Input2_Terms_Index]
    			///<R1=AXB建立13x13的矩阵,R2=R1'把矩阵转成169x1的列向量
    			for (i = 0; i < 169; i++)
    				for (j = 0; j < 13; j++)
    				{
    					// R1(E, EC)与U进行取小运算
    					if (R2[i] < Output_Terms_Membership[Output_Terms_Index][j])
    						R3[i][j] = R2[i];
    					else
    						R3[i][j] = Output_Terms_Membership[Output_Terms_Index][j];
    					// R进行取大运算,为所有规则模糊关系的并集
    					if (R3[i][j] > R[i][j])
    						R[i][j] = R3[i][j];
    				}
    		}
    
    
    	/*************************对于每种可能的E、EC的精确取值模糊化后进行推理得到模糊输出Cd,Cd=(AdxBd)oR*************************/
    	for (Input1_value_index = 0; Input1_value_index < 13; Input1_value_index++) {
    		for (Input2_value_index = 0; Input2_value_index < 13; Input2_value_index++)
    		{
    			for (j = 0; j < 13; j++)
    				Cd[j] = 0;
    			int kd = 0;
    			float temp = 0;
    			Max_Input1_value = E_MAX(Input1_value_index);	///<找出误差隶属度最大的语言值
    			Max_Input2_value = EC_MAX(Input2_value_index);	///<找出误差变化率隶属度最大的语言值
    			for (i = 0; i < 13; i++)
    				for (j = 0; j < 13; j++)
    				{
    					// E(Ad)和EC(Bd)进行取小运算
    					if (Input1_Terms_Membership[Max_Input1_value][i] < Input2_Terms_Membership[Max_Input2_value][j])
    						AdBd1[i][j] = Input1_Terms_Membership[Max_Input1_value][i];
    					else
    						AdBd1[i][j] = Input2_Terms_Membership[Max_Input2_value][j];
    					AdBd2[kd] = AdBd1[i][j];
    					kd++;
    				}
    			for (i = 0; i < 169; i++)
    				for (j = 0; j < 13; j++)
    				{
    					// 模糊矩阵的合成,将乘积运算换成“取小”,将加法运算换成“取大”
    					if (AdBd2[i] < R[i][j])
    						temp = AdBd2[i];
    					else
    						temp = R[i][j];
    					if (temp > Cd[j])
    						Cd[j] = temp;
    				}
    
    
    			/*************************去模糊化(加权平均法),计算实际输出*************************/
    			float sum1 = 0, sum2 = 0;
    			float OUT;
    			for (i = 0; i < 13; i++)
    			{
    				sum1 = sum1 + Cd[i];
    				sum2 = sum2 + Cd[i] * SPEED[i];
    			}
    			OUT = (int)(sum2 / sum1 + 0.5);///<四舍五入
    			Fuzzy_Table[Input1_value_index][Input2_value_index] = OUT;
    			cout << OUT << ",";
    		}
    		cout << endl;
    	}
    }
    

    3.模糊查询表设置车速

    将模糊查询表复制进入代码程序,将实际的e和ec映射到论域中后,在模糊查询表中查询结果并设置目标车速。

    int_16 Fuzzy_Table[13][13]= 
    { 
    203,211,211,211,226,226,230,230,228,210,210,210,210,
    209,221,221,221,238,238,241,241,237,231,231,231,227,
    209,221,221,221,238,238,241,241,237,231,231,231,227,
    209,221,221,221,238,238,241,241,237,231,231,231,227,
    215,238,238,238,245,245,266,266,246,237,237,237,232,
    215,238,238,238,245,245,266,266,246,237,237,237,232,
    218,250,250,250,276,276,283,283,280,245,245,245,216,
    218,250,250,250,276,276,283,283,280,245,245,245,216,
    232,240,240,240,250,250,271,271,246,236,236,236,217,
    226,230,230,230,236,236,239,239,236,214,214,214,208,
    226,230,230,230,236,236,239,239,236,214,214,214,208,
    226,230,230,230,236,236,239,239,236,214,214,214,208,
    211,211,211,211,226,226,230,230,228,208,208,208,203
    }  ;
    
    int_16 get_speed_set(void) {
    	int_16 E = 0, EC = 0;
    	int_16 speed_target;
    	static int_16 re_pos = 0, ek = 0, eck = 0;
    	float ke = 400, kec = 10;
    	ek = 2500 - row;
    	eck = 2500 - row - re_pos;
    	re_pos = ek;
    
    	if (ek > 0) {
    
    		E = (int_32)(ek / ke + 0.5);
    	}
    	else {
    
    		E = (int_32)(ek / ke - 0.5);
    	}
    	//将E的论域转换到模糊控制器的论域
    	if (E > 6)
    		E = 6;
    	else if (E < -6)
    		E = -6;
    	if (eck > 0) {
    
    		EC = (int_16)(eck / kec + 0.5);
    	}
    	else {
    
    		EC = (int_16)(eck / kec - 0.5);
    	}//将EC的论域转换到模糊控制器的论域
    	if (EC > 6)
    		EC = 6;
    	else if (EC < -6)
    		EC = -6;
    
    	speed_target = (int_16)(Fuzzy_Table[E + 6][EC + 6]);
    	return speed_target ;
    }
    

    三、总结

    本文首先对PID控制器进行了简单的阐述,并应用于车速控制中。然后引入模糊控制对目标车速进行设置,实现速度的平稳过渡。PID算法和模糊控制算法在保证行驶平稳性的前提下,最大幅度地提升小车的行驶速度。

    参考资料
    [1]详细讲解PID控制
    [2]PID控制算法原理(抛弃公式,从本质上真正理解PID控制)
    [3]初识PID-搞懂PID概念
    [4]模糊控制——基本原理
    [5]基于单目视觉的智能车速度模糊控制系统
    [6]模糊算法在智能车控制中的应用

    展开全文
  • MSP432E401Y单片机智能小车PID调速代码

    千次阅读 2018-06-19 17:12:05
    * Description:PID处理函数 * 引脚: * * Author: Robin.J ***************************************************************************/ #include &lt;PID.h&gt; #include "ti/devices/msp43....
  • 智能车代码

    2013-03-30 16:26:24
    第七届智能车代码,有角度模糊控制,pid控制等等
  • 模糊pid和模糊控制模糊pid和模糊控制智能车编程实现的智能车编程实现
  • 智能车模糊控制

    2018-11-03 22:14:58
    根据偏差与斜率构建模糊规则表,确定P,D参数,用于舵机转向与电机控速。获得智能车国一
  • 小车pid控制

    2018-08-18 19:40:04
    使用MDK编写的STM32F103ZET6的智能车下位控制程序,使用串口控制
  • 模糊PID控制方向写在前面代码讲解模糊PID调试方法附程序 写在前面 我写了一篇总的博客,分享了我参加了十五届智能车竞赛的经历哦~ 2020第十五届全国大学生智能汽车竞赛——基础四轮组入门看这一篇就够了! 我采用的...
  • 备战第16届智能车-控制处理进阶-模糊PID算法

    千次阅读 多人点赞 2020-11-22 14:36:41
    备战第16届智能车-控制处理进阶-模糊PID算法一、前言二、代码部分1、模糊分布表2、计算模糊完成的Kp\Kd三、总结 一、前言 模糊PID算法近几年被广泛用于智能车竞赛之中 博主将用最简单的方式让初学者明白如何使用 ...
  • 智能车PID

    千次阅读 多人点赞 2020-01-22 10:43:38
    放假前答应学长写一篇关于pid控制电机的文章,耽搁了几天着手开始写。首先感谢学长带我走上飞思卡尔智能车比赛的路,万分感谢。 我们要了解pid是什么,就得知道pid是干什么的。因为没有通过专业的学过pid的用法,...
  • 主要讲解PID的C语言实现,可以用在工程应用中,也可以用在智能车控制中,是一个很好的教程
  • 智能车PID_原理

    千次阅读 多人点赞 2019-04-03 22:04:43
    为了实现PID控制所需要的等间隔采样,我们使用了一个定时中断,每2ms进行一次数据采样和PID计算。与此并行,系统中还设计了一个转速脉冲检测中断,从而实现了转速检测。为了调试的需要,程序中还在main{}函数中加入...
  • 智能车控制算法 —— PID (学习笔记)

    千次阅读 多人点赞 2020-04-24 18:53:55
    PID控制:一种调节器控制规律为比例、积分、微分的控制。其中:P:比例(proportion)、I:积分(integral)、D:导数(derivative) 式子中Kp为比例系数,Ti为积分时间参数,Td为微分时间常数。 各个参数的意义作用...
  • 适合智能车竞赛入门使用 ov7620经典摄像头 stm32主控 IAR工程 包括图像采集 二值化 中线提取 平滑处理 平均滤波 舵机pid控制 代码很规范适合大一大二同学智能车竞赛入门
  • PID调速智能车

    2017-12-29 15:00:24
    嵌入式智能小车,通过PID调节速度,实时追踪前车达到控制目的
  • STC15智能车所有代码

    2018-02-21 22:08:57
    资源内包括各个模块单独的代码,以及融合在一起的代码,使用的是STC15W单片机,包括红外循迹YL-70 模块,超声波HC-SR04测距模块,NRF24...最终是将所有模块整合在一起,实现智能车红外循迹,自主避障,双车通信等功能。
  • PID智能车中的简单使用

    万次阅读 多人点赞 2018-03-10 15:35:22
    在一个控制系统中,需要闭环控制就势必会有采样,而采样就必然有采样周期。我在学校的时候做过智能车和四旋翼。智能车是根据摄像头或者电磁...在这个校准的过程中,就要用到PID了,不同的是,智能车的方向校准是单...
  • 智能车新手入门】-位置式、增量式PID实现代码

    万次阅读 多人点赞 2014-10-19 17:11:32
    PID控制是大家在智能车制作中碰到最常见的算法,它主要分两种:位置式和增量式。下面来谈谈这两种PID的特点以及代码实现。 1. 位置式PID 特点:位置式PID用到了过去所有误差值的积分,因此与过去的整个状态有关。...
  • 在疫情期间比较无聊,在某宝买了一个智能小车底盘和一堆零件,基于Arduino Due和树莓派进行开发,Due负责底层控制,树莓派进行上层控制器开发,比如斯坦利控制器或者模型预测控制器进行轨迹跟踪。本次采用Simulink...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 1,552
精华内容 620
关键字:

智能车pid控制代码