1. 从PID到ADRC为什么我们需要“自抗扰”如果你在工业控制、机器人或者电力电子领域摸爬滚打过一段时间对PID控制器一定不会陌生。它结构简单鲁棒性不错是工程师们工具箱里的“瑞士军刀”。但用久了你肯定也遇到过它的“脾气”面对快速变化的设定值超调量让你头疼系统存在未知扰动时需要反复调参才能勉强稳住更别提那些非线性、强耦合的复杂对象PID常常显得力不从心。这时候你可能会听到一个词自抗扰控制。ADRC全称Active Disturbance Rejection Control中文名“自抗扰控制”听起来就比PID“主动”得多。它不像PID那样把系统内部未建模的动态和外部扰动都当作需要被动“抑制”的麻烦而是换了个思路我把所有“不知道的”、“不确定的”东西统统打包成一个总扰动然后实时地把它“观测”出来再“补偿”掉。这个思想就像给控制系统装上了一双“眼睛”和一个“补偿器”让它能“看见”并主动对抗干扰而不是等干扰产生了影响再去“亡羊补牢”。我第一次接触ADRC是在一个伺服电机的位置跟踪项目里。传统的PID前馈控制在面对负载突变和摩擦力非线性变化时跟踪误差会瞬间变大需要很保守的增益来保证稳定牺牲了动态性能。引入ADRC框架后最直观的感受是控制器“聪明”了。它不再仅仅依赖误差的比例、积分、微分而是通过一个叫做“扩张状态观测器”的核心部件实时估算出包括负载转矩变化、摩擦力、模型误差在内的总扰动并予以抵消。调试过程从“盲人摸象”般的参数试凑变成了更有逻辑的带宽整定。当然ADRC不是银弹它有自己的“脾气”和适用边界但理解它无疑是打开现代鲁棒控制思想的一扇重要窗户。2. ADRC的核心三件套TD、ESO与NLSEF自抗扰控制器的结构清晰主要由三个部分组成跟踪微分器、扩张状态观测器和非线性状态误差反馈控制律。这三者协同工作构成了ADRC区别于传统方法的骨架。2.1 跟踪微分器为指令“整形”在PID控制中我们常常直接使用阶跃信号作为设定值。但对于一个物理系统瞬间的阶跃变化意味着需要无穷大的加速度或力这在实际中不可能实现强行跟踪必然导致超调和振荡。TD的作用就是为参考输入信号安排一条合理、光滑的过渡轨迹。你可以把TD理解为一个“运动规划器”。它接收一个跳变的指令信号v比如从位置A到位置B然后输出两个信号一个是安排后的过渡信号v1这个信号是光滑的其变化率是有限的另一个是v1的微分信号v2。v1用来替代原始指令作为被控对象的跟踪目标v2则可以作为前馈信号使用。最经典的TD由韩京清研究员提出其离散形式如下function [v1, v2] TD(v, h, r, h0) % v: 输入指令 % h: 积分步长 % r: 速度因子决定跟踪快慢 % h0: 滤波因子决定光滑程度 fh fhan(v1 - v, v2, r, h0); v1 v1 h * v2; v2 v2 h * fh; end function fh fhan(x1, x2, r, h0) d r * h0; d0 h0 * d; y x1 h0 * x2; a0 sqrt(d*d 8*r*abs(y)); a if abs(y) d0 then (sign(y)*(a0-d)/2) else (x2 y/h0); fh -r * if abs(a) d then sign(a) else a/d; end这里的fhan是一个最速控制综合函数它保证了v1能以最快速度无超调地跟踪v。参数r越大跟踪速度越快h0越大滤波效果越强输出越光滑。TD的引入从根本上避免了因设定值突变引起的控制器输出饱和与系统冲击是提升控制品质的第一步也是常被初学者忽略的一步。2.2 扩张状态观测器系统的“透视眼”ESO是ADRC的灵魂也是其“自抗扰”能力的来源。它的核心思想非常巧妙将系统内部未建模动态和外部未知扰动统一视为一个作用于系统的“总扰动”并将这个总扰动作为系统的一个新的扩张状态变量进行观测。考虑一个常见的二阶系统很多工程对象可简化为二阶ẍ f(x, ẋ, w(t), t) b * u其中f(·)包含了已知/未知的系统动态和外部扰动w(t)b是控制增益可能已知或未知。ESO的做法是令x3 f(·)作为一个新的状态将原系统扩张为ẋ1 x2ẋ2 x3 b * uẋ3 ḟ假设扰动变化率有界然后我们为这个扩张后的系统设计一个状态观测器通常采用龙伯格观测器结构来同时观测原系统状态x1位置x2速度以及这个代表总扰动的扩张状态x3。一个典型的线性ESOLESO的离散实现如下function [z1, z2, z3] LESO(y, u, h, beta01, beta02, beta03, b0) % y: 系统输出测量值 (x1) % u: 控制输入 % h: 采样时间 % beta01, beta02, beta03: 观测器增益 % b0: 控制增益b的估计值 e z1 - y; % 观测误差 fe1 fal(e, 0.5, delta); % 非线性函数线性ESO中可简化为e fe2 fal(e, 0.25, delta); % 状态更新欧拉法 z1 z1 h * (z2 - beta01 * e); z2 z2 h * (z3 b0 * u - beta02 * fe1); z3 z3 h * (-beta03 * fe2); end观测器增益beta需要配置通常将其极点配置在同一个位置-ω_o观测器带宽则有beta013ω_o, beta023ω_o^2, beta03ω_o^3。ω_o越大观测器收敛越快对扰动的估计也越及时但对测量噪声也越敏感需要在性能与鲁棒性之间折衷。最终z1和z2分别是系统状态x1和x2的观测值而z3就是对总扰动f(·)的实时估计值。有了这个估计值我们就可以在控制律中将其抵消。2.3 非线性状态误差反馈简洁有力的控制律在PID中控制量是误差的比例、积分、微分项的线性加权和。在ADRC的早期形式中韩京清研究员提出用非线性函数fal(e, α, δ)来代替线性增益构成非线性状态误差反馈律NLSEF旨在获得“小误差大增益大误差小增益”的非线性特性提高响应速度的同时抑制超调。fal函数定义如下function f fal(e, alpha, delta) if abs(e) delta f e / (delta^(1-alpha)); else f (abs(e)^alpha) * sign(e); end end其中0 alpha 1delta 0。当误差e很小时函数呈现大增益线性特性当误差e较大时呈现小增益非线性特性。那么结合TD和ESONLSEF的控制量计算为e1 v1 - z1安排后指令与观测位置的误差e2 v2 - z2指令微分与观测速度的误差u0 β1 * fal(e1, α1, δ) β2 * fal(e2, α2, δ)初步控制量最后利用ESO观测到的总扰动z3进行补偿得到最终的控制量u (u0 - z3) / b0这一步是ADRC的精髓u0是基于“理想无扰动模型”计算出的控制力而z3是观测到的实际扰动(u0 - z3)就意味着用控制力去抵消扰动剩下的部分u0才真正用于驱动系统跟踪指令。由于z3实时变化这种补偿是动态的、自适应的。在实际工程中为了简化参数整定线性组合即α1α21fal退化为线性配合线性ESOLADRC的应用更为广泛其性能已经能在大多数场景下令人满意。3. 从理论到代码一个电机电流环的LADRC实例理论说得再多不如一行代码来得实在。我们以一个最典型的应用场景——永磁同步电机的电流环控制为例看看如何用MATLAB/Simulink实现一个线性ADRC。电流环是电机控制的内环要求响应快、抗扰动能力强对抗反电动势、电阻电感参数变化等是ADRC大显身手的地方。假设我们的被控对象是电机的q轴电流回路其近似模型为一阶惯性环节G(s) I_q(s) / U_q(s) 1 / (L s R)其中L是电感R是电阻。在实际中L和R会随温度、磁饱和而变化反电动势、逆变器非线性等也会作为扰动出现。我们可以将其写为状态空间形式di/dt -(R/L) * i (1/L) * u d(t)令a -R/L,b 1/L则di/dt a * i b * u d(t)。这里d(t)就包含了模型误差和外部扰动。3.1 一阶系统的线性ADRC设计对于一阶系统我们设计一个二阶ESO因为要扩张一个状态来观测总扰动。令x1 i电流x2 f总扰动包含a*i和d(t)则扩张系统为ẋ1 x2 b * uẋ2 ḟ设计龙伯格观测器其连续时间形式为ż1 z2 b0*u β1*(i - z1)ż2 β2*(i - z1)其中z1是电流观测值z2是总扰动观测值b0是b的估计值1/L的标称值。将观测器极点配置在-ω_o则有β1 2ω_o,β2 ω_o^2。控制律非常简单u0 kp * (i_ref - z1)i_ref为电流参考值来自速度环u (u0 - z2) / b0看这就是一阶LADRC的全部。它甚至比PI控制器还简单只有一个控制器增益kp和一个观测器带宽ω_o需要调节。3.2 MATLAB函数实现下面是一个用于离散系统数字控制的S函数或MATLAB Function模块的实现示例function u ADRC_Current_Loop(i_ref, i_meas, h, omega_o, kp, b0) % i_ref: 电流参考值 % i_meas: 电流测量值 % h: 控制周期秒 % omega_o: 观测器带宽 (rad/s) % kp: 控制器比例增益 % b0: 控制增益估计值 persistent z1 z2; % 声明为持久变量保持状态 if isempty(z1) z1 0; z2 0; % 初始化 end % 1. 计算观测器增益 beta1 2 * omega_o; beta2 omega_o * omega_o; % 2. ESO状态更新前向欧拉离散化 e z1 - i_meas; z1 z1 h * (z2 b0 * u_prev - beta1 * e); % 注意这里用上一拍的u z2 z2 h * (-beta2 * e); % 3. 控制律计算 e_control i_ref - z1; % 使用观测状态而非直接测量有滤波效果 u0 kp * e_control; u (u0 - z2) / b0; % 4. 限幅实际驱动器有电压限制 u_max 12; % 假设母线电压12V u_min -12; u min(max(u, u_min), u_max); u_prev u; % 为下一拍ESO计算保存 end几个关键实操细节离散化上述代码使用了前向欧拉法简单但稳定性稍差。对于高精度或长采样周期建议使用更精确的方法如双线性变换Tustin来离散化连续ESO方程。u_prev的使用在ESO的z1更新方程中我们使用了上一控制周期的u。这是因为在数字控制中当前周期计算出的u在本周期内还未来得及作用于对象并产生新的测量值i_meas。这是一种典型的处理方式。观测状态反馈控制误差e_control使用的是i_ref - z1而非i_ref - i_meas。z1是ESO观测出的状态它本身已经对测量噪声有一定的滤波作用这比直接使用可能含有噪声的测量值更优。参数整定b0取标称值1/L_nominal。ω_o通常设为(3~10)*ω_c其中ω_c是你期望的闭环带宽。kp可近似按ω_c来选对于一阶系统kp ≈ ω_c。调试时先调ω_o使扰动观测快速且平稳再调kp满足动态性能。3.3 在Simulink中搭建与调试在Simulink中你可以将上面的代码封装成一个MATLAB Function模块。然后构建一个简单的测试模型Ref Signal (Step) -- ADRC模块 -- Plant (1/(LsR)) -- Scope (输出电流) ↑ | |------------------------------| (反馈电流)在Plant模块中可以加入一个阶跃信号作为负载扰动或者让L、R参数缓慢变化来测试ADRC的抗扰能力。调试心得观测器带宽ω_o是双刃剑调得过高z2扰动估计会高频抖动可能将测量噪声放大引入控制量调得过低扰动估计滞后补偿效果差。一个实用的方法是先给一个适中的ω_o观察z2的波形它应该能平滑地跟踪上实际扰动的变化趋势。如果噪声大就降低ω_o或在前级加入低通滤波但会引入相位滞后。b0不准的影响b0是控制增益的估计值。如果b0大于真实b则补偿项z2/b0会偏小导致扰动抵消不完全如果b0小于真实b则补偿过度可能引起振荡。ADRC对b0的精度要求并不苛刻通常有 ±20%-50% 的误差仍能稳定工作这是其鲁棒性的体现。但为了最佳性能应尽量准确。与PI对比在同样的带宽要求下ADRC的阶跃响应超调通常更小恢复时间更短尤其是在存在扰动时。你可以同时搭建一个PI控制器进行对比PI的参数可以用零极点对消或经验公式来整定使其闭环带宽与ADRC的ω_c大致相当。4. 参数整定从玄学到科学ADRC的参数比PID少但整定逻辑不同初学者可能觉得无从下手。其实对于线性ADRC有一套相对系统的带宽参数化方法让整定变得有章可循。4.1 带宽参数化法对于前面提到的二阶系统LADRC针对位置控制等其标准形式通常有三个参数控制器带宽ω_c、观测器带宽ω_o和控制增益估计值b0。确定b0这是最物理的一个参数。它就是你的控制输入到系统输出的近似增益。例如对于电机位置控制u是电压输出是角度那么b0可以粗略估计为(Kt / J)其中Kt是转矩常数J是转动惯量。取标称值即可即使有误差ESO也能在一定程度上补偿。确定ω_c这取决于你期望的闭环系统响应速度。ω_c越大响应越快但控制量需求越大对噪声也越敏感。一个经验法则是ω_c可以取为系统开环带宽的 3~5 倍但不能超过你执行器如电机、阀门的物理响应能力或采样频率的1/10尼奎斯特限制。例如对于一个响应较慢的温度系统ω_c可能只有 0.1 rad/s对于一个快速的电流环ω_c可以达到 1000 rad/s 以上。确定ω_o观测器需要比控制器更快地估计出状态和扰动才能提供及时的补偿。通常ω_o取(3~10) * ω_c。这个比例因子需要权衡抗扰性能ω_o越大扰动估计越快抗扰能力越强。噪声抑制ω_o越大观测器对测量噪声越敏感z2会抖动可能将噪声放大后注入控制量。鲁棒性ω_o过大可能降低观测器对模型不确定性的鲁棒性。一个经典的调试流程是a. 固定一个适中的ω_o/ω_c比例比如 5。 b. 从小到大调节ω_c观察系统跟踪响应直到达到满意的速度如上升时间。 c. 保持ω_c不变调节ω_o。增加ω_o观察系统在施加扰动如负载突变后的恢复速度同时观察控制量u的波形如果出现高频毛刺说明ω_o太高引入了噪声。 d. 微调b0。如果发现系统在扰动下存在稳态误差或轻微振荡可以适当增大或减小b0通常在 ±30% 范围内调整。4.2 整定中的常见问题与对策系统振荡甚至发散可能原因1ω_c过高超出了被控对象能响应的带宽。对策降低ω_c。可能原因2ω_o过高且测量噪声大导致观测器失稳或控制量高频振荡。对策降低ω_o或在反馈通道中加入一阶低通滤波器1/(τs1)τ取1/(5~10*ω_o)。可能原因3b0严重偏离真实值例如差一个数量级。对策重新估算b0。可以通过阶跃响应测试b0 ≈ Δy / (Δu * T)其中Δy是输出变化Δu是输入阶跃T是近似时间常数。抗扰效果不明显可能原因1ω_o过低扰动估计太慢补偿滞后。对策提高ω_o。可能原因2b0过大导致补偿量z2/b0太小。对策适当减小b0。可能原因3扰动变化过快超出了观测器带宽。对策如果可能提高ω_o如果受限于噪声则需从硬件或源头降低扰动频率。响应速度慢可能原因1ω_c过低。对策提高ω_c。可能原因2ω_o过低导致状态观测z1滞后使得基于z1的误差计算不准确。对策提高ω_o。我的个人经验是对于大多数工业过程可以先从ω_o 5 * ω_c开始。ω_c的初始值可以设为系统所需上升时间t_r对应的频率粗略估计为ω_c ≈ 2π / t_r。然后遵循“先调观测器再调控制器”的原则优先保证观测器能稳定、平滑地估计出状态和扰动再调整控制器增益来满足动态性能。5. 进阶话题当ADRC遇到现实挑战理论分析和仿真都很美好但把ADRC部署到真实的电机驱动器、机械臂或化工过程中会遇到一系列仿真中不曾出现的问题。5.1 测量噪声与ESO的滤波特性ESO本身就是一个状态观测器它天然地对测量噪声有一定的滤波作用因为观测器方程可以看作是一个动力系统其带宽ω_o决定了其通过高频信号的能力。但这不是万能的。当传感器噪声较大特别是噪声频率接近或高于ω_o时z2扰动估计会严重失真高频噪声会被放大并注入控制量u可能激发系统未建模的高频动态甚至导致硬件损坏。解决方案降低ω_o最直接的方法但牺牲了扰动估计速度。前置滤波器在测量信号y进入ESO之前加一个一阶低通滤波器1/(τs1)。τ的选择很关键τ太大会引入相位滞后影响观测和控制性能τ太小滤波效果差。通常τ取1/(5~10*ω_o)这样滤波器的截止频率远高于观测器带宽相位滞后较小。注意这个滤波器是物理信号调理的一部分需要在设计ESO时将其动态考虑进去或者将其近似为纯延时在控制器设计时预留相位裕度。改进ESO结构可以采用降阶ESO或者设计带噪声统计特性的卡尔曼滤波器形式的ESO但这会大大增加复杂性。5.2 采样延迟与计算延迟在数字控制中从信号采样、算法计算到PWM更新存在不可避免的延迟。通常至少有一个控制周期T_s的延迟。这个延迟会降低相位裕度尤其在高带宽 (ω_c) 时影响显著可能导致系统不稳定。影响与对策对ESO的影响延迟使得观测器基于“过时”的信息进行预测降低了观测精度。在离散化ESO方程时采用更精确的方法如零阶保持器离散化比简单的欧拉法更能反映连续特性。在代码实现中如前所述使用上一拍的u来更新当前状态就是一种对计算延迟的补偿。对控制性能的影响延迟限制了可实现的控制带宽。经验上ω_c应小于1/(10*T_s)以保证足够的稳定裕度。如果系统要求高带宽就必须使用更快的处理器缩短T_s。补偿方法可以在控制律中引入史密斯预估器来补偿已知的固定延迟但这会进一步增加复杂度。对于ADRC更务实的做法是在设计带宽时就为延迟留出足够的裕量。5.3 控制量饱和与抗积分饱和ADRC的控制律u (u0 - z2)/b0是瞬时计算的没有积分项因此理论上不存在PID中的积分饱和问题。但是当u0很大例如设定值大幅跳变或z2很大巨大扰动时计算出的u可能超出执行器如电机驱动器、阀门的物理限幅[u_min, u_max]。饱和带来的问题扰动估计失真ESO的更新依赖于控制输入u。如果实际执行的是饱和后的u_sat而ESO模型里用的却是计算出的未饱和的u就会导致ESO的模型与实际过程不匹配z2的估计会产生偏差甚至发散。解决方案——“Clamping”技术这是处理饱和问题的标准方法。在ESO的更新方程中不使用计算出的理想控制量u而使用经过限幅后的实际施加于对象的控制量u_sat。修改前面的代码% ... 计算 u ... u (u0 - z2) / b0; u_sat min(max(u, u_min), u_max); % 实际执行的控制量 % ESO更新时使用 u_sat z1 z1 h * (z2 b0 * u_sat - beta1 * e); z2 z2 h * (-beta2 * e);这个简单的改动保证了ESO的模型始终与真实被控对象“同步”是工程实现中至关重要的一步。5.4 非线性与时变对象的适应性ADRC的核心优势在于其将非线性、时变特性都视为“总扰动”的一部分进行观测和补偿。但这并不意味着它是万能的。对于严重非线性如果非线性特性如死区、滞环、库伦摩擦是快变的其微分ḟ很大这就要求ESO的带宽ω_o非常高才能跟上可能不现实。此时最好采用前馈补偿或基于模型的补偿先消除主要的非线性再用ADRC处理残余扰动和不确定性。例如对于已知的库伦摩擦可以加入基于速度符号的补偿力。对于参数慢时变ADRC通常能很好地处理。因为ESO会持续地估计出由参数变化引起的扰动。对于控制增益b的时变这是ADRC的一个弱点。b0是固定值如果真实的b变化很大补偿公式u (u0 - z3)/b0就不再准确。一种自适应思路是在线辨识b的变化但会显著增加复杂度。在实践中如果b的变化范围已知例如电机电感随电流变化 ±30%可以取一个折中的b0ADRC通常仍能保持稳定但性能会有所下降。6. 工程实践中的选择LADRC vs. NLADRC vs. PID面对一个具体项目该如何选择这里谈谈我的看法。PID仍然是首选如果系统相对简单、线性、扰动可测或模型已知。它的优势是简单、直观、工程师熟悉、几乎所有硬件平台都有现成库。当性能要求不是极端且你有时间精细调参时PID往往够用。线性ADRC当你面临模型不确定、有未知扰动、且希望减少调参工作量时LADRC是一个强有力的升级选项。它只有ω_c,ω_o,b0三个核心参数物理意义相对明确。对于大多数工业应用电机控制、运动控制、过程控制LADRC的性能提升已经非常显著且易于实现和调试是我最推荐的形式。非线性ADRC保留了原始的非线性fal函数和TD。理论上在过渡过程安排和误差处理上更优。但参数更多α1, α2, δ, r, h0, β...整定更复杂对计算资源要求也稍高。除非你对超调、过渡过程有极致要求并且有足够的经验和时间进行参数整定否则NLADRC的性价比不如LADRC。在很多应用中用线性TD即一个二阶或三阶线性滤波器代替非线性TD用线性反馈代替NLSEF得到的性能与NLADRC相差无几但复杂度大大降低。选型建议流程图问题需要控制一个存在未知扰动/模型不确定的系统 | |--是-- 系统动态是否相对平缓且对超调无极端要求 | | | |--是-- 优先尝试 **PID 前馈/扰动观测**。简单可靠。 | | | |--否-- 系统阶数是否明确一阶、二阶为主 | | | |--是-- 首选 **线性ADRC (LADRC)**。参数少性能提升明显。 | | | |--否-- 系统是否为高阶、强非线性 | | | |--是-- 考虑将系统解耦为多个一阶/二阶子系统分别用ADRC控制。 | | 或者投入资源进行系统辨识和模型化再设计高级控制器。 | | | |--否-- 对于有经验的开发者可尝试 **非线性ADRC**追求极限性能。 | |--否-- 模型已知且准确扰动可测 -- 使用基于模型的控制如状态反馈、MPC等。最后我想强调的是ADRC是一种优秀的控制思想但它不是要完全取代PID。它为我们提供了一种处理不确定性和扰动的新范式。在实际项目中我常常采用一种“渐进”策略先用PID实现基本功能如果性能不满足特别是抗扰性差再考虑引入LADRC来替换内环如电流环、速度环的PID控制器往往能取得事半功倍的效果。理解其原理掌握其实现和调试方法能让你的控制工具箱里多一件应对复杂局面的利器。