3、Ziegler-Nichols整定法(时域法):基于阶跃响应的ZN法、临界比例度法、参数计算表
说到PID参数整定,Ziegler-Nichols法(简称ZN法)绝对是绕不开的经典。我入行那会儿,师父丢给我的第一本手册就是Ziegler和Nichols在1942年发表的论文。说实话,那时候觉得这方法有点老古董了。但后来在实际项目中吃了几次亏,才明白经典之所以是经典,是因为它真的能打。
ZN法说白了就两种思路:一种看系统的阶跃响应曲线,另一种找系统的临界振荡点。咱们一个一个聊。
3.1 基于阶跃响应的ZN法(开环整定)
这个方法适合那些开环稳定的对象。比如温度控制、液位控制,你给它一个阶跃信号,它慢慢悠悠地爬到稳态值。嗯,这时候就能用上这个办法了。
具体怎么做?我习惯分三步走:
- 做阶跃实验:系统开环,给一个幅度合适的阶跃输入。记录输出响应曲线。
- 找特征参数:从曲线上提取两个关键值——滞后时间L和上升时间T(或者叫时间常数τ)。
- 查表算参数:根据L和T的比值,套用ZN参数表。
这里有个细节要注意:阶跃幅度不能太大,否则系统可能进入非线性区;也不能太小,否则信噪比不够,曲线毛刺太多。我个人习惯取稳态值的10%~15%。
核心公式:
对于一阶惯性加纯滞后系统(FOPDT):G(s) = K * e^(-Ls) / (τs + 1)
其中:L = 滞后时间,τ = 时间常数,K = 稳态增益
拿到L和τ之后,直接套用ZN参数计算表:
| 控制器类型 | Kp | Ti | Td |
|---|---|---|---|
| P | τ / (K * L) | — | — |
| PI | 0.9 * τ / (K * L) | 3.33 * L | — |
| PID | 1.2 * τ / (K * L) | 2 * L | 0.5 * L |
你想想看,这个表其实挺有意思的。比例系数Kp跟τ/L成正比,说白了就是系统响应越慢(τ大),或者滞后越小(L小),Kp就可以给得越大。积分时间Ti跟滞后时间L直接挂钩,滞后越大,积分越慢,防止积分饱和。
我的经验:用这个方法整定出来的参数,通常系统会有10%~20%的超调。如果现场不允许超调,我建议把Kp打八折,Ti翻倍。我在一个化工反应釜的温度控制项目里就是这么干的,效果还不错。
3.2 临界比例度法(闭环整定)
这个方法适合那些开环不稳定的对象,或者你懒得做开环实验的场合。说白了就是让系统先振荡起来,找到临界点。
操作步骤也不复杂:
- 系统闭环,把积分和微分都关掉(Ti = ∞,Td = 0)。
- 慢慢增大比例增益Kp,直到系统输出出现等幅振荡。
- 记录此时的临界增益Ku和临界振荡周期Tu。
这里有个坑——我曾经遇到过,系统还没到等幅振荡就先发散掉了。为什么会这样?因为有些系统的非线性太强,或者执行机构有饱和限制。遇到这种情况,我建议把目标定为「出现明显的持续振荡」就行,不一定非要等幅。
拿到Ku和Tu之后,查另一张表:
| 控制器类型 | Kp | Ti | Td |
|---|---|---|---|
| P | 0.5 * Ku | — | — |
| PI | 0.45 * Ku | 0.83 * Tu | — |
| PID | 0.6 * Ku | 0.5 * Tu | 0.125 * Tu |
警告:临界比例度法会让系统进入振荡状态。对于某些不允许振荡的场合(比如精密位置控制、医疗设备),千万别用这个方法。我曾经在一个伺服电机项目里试过,结果电机嗡嗡响,差点把机械结构震散架了。
3.3 两种方法的对比与选择
说了这么多,到底该用哪个?我个人的选择原则是这样的:
- 开环阶跃响应法:适合大多数工业过程控制,比如温度、压力、流量。安全,不会让系统振荡。但前提是你得能做开环实验。
- 临界比例度法:适合那些开环实验不好做的系统,或者你赶时间。但风险就是系统会振荡,得悠着点。
其实吧,这两种方法整定出来的参数都只是「初始值」。真正好用的参数,还得在现场微调。我一般用ZN法算个大概,然后根据实际响应再调一调Kp、Ti、Td。说白了,ZN法就是个起点,不是终点。
3.4 代码实现示例
最后,给一段我常用的Python代码,用来计算ZN参数。你拿去改改就能用:
def zn_open_loop(L, tau, K, controller_type='PID'):
"""
基于阶跃响应的ZN法参数计算
L: 滞后时间
tau: 时间常数
K: 稳态增益
"""
if controller_type == 'P':
Kp = tau / (K * L)
Ti = None
Td = None
elif controller_type == 'PI':
Kp = 0.9 * tau / (K * L)
Ti = 3.33 * L
Td = None
elif controller_type == 'PID':
Kp = 1.2 * tau / (K * L)
Ti = 2 * L
Td = 0.5 * L
return Kp, Ti, Td
def zn_closed_loop(Ku, Tu, controller_type='PID'):
"""
临界比例度法参数计算
Ku: 临界增益
Tu: 临界振荡周期
"""
if controller_type == 'P':
Kp = 0.5 * Ku
Ti = None
Td = None
elif controller_type == 'PI':
Kp = 0.45 * Ku
Ti = 0.83 * Tu
Td = None
elif controller_type == 'PID':
Kp = 0.6 * Ku
Ti = 0.5 * Tu
Td = 0.125 * Tu
return Kp, Ti, Td
嗯,代码不长,但够用。你拿到参数之后,记得先在仿真环境里跑一跑,别直接往现场怼。我在一个项目里就因为太自信,参数直接上机,结果系统超调了30%,差点把阀门给干废了。
好了,ZN法就聊到这儿。下一章咱们聊聊另一种经典方法——Cohen-Coon整定法,那个更适合大滞后系统。