电机参数辨识与在线自整定 - 第4节
电阻辨识方法:直流注入法原理与实现
电阻辨识,说白了就是搞清楚电机绕组的直流电阻到底是多少。你可能会问,这玩意儿不是铭牌上写着吗?嗯,铭牌上的数据是常温下的标称值,实际运行中温度一变,电阻也跟着变。我做过一个项目,电机在冷态和热态下电阻差了将近20%,电流环的响应完全不一样。
直流注入法是目前工业界最常用的方法。原理很简单——给电机绕组通一个直流电压,测电流,然后用欧姆定律算电阻。但这里有个坑:电机是感性负载,直接通直流会有电气过渡过程,你得等电流稳定了再采样。
基本原理
对于永磁同步电机,定子绕组的电气方程是:
u = R·i + L·(di/dt) + e
当注入直流时,di/dt = 0,反电动势 e = 0(电机静止)。方程就简化为:
u = R·i
所以 R = u / i。听起来简单吧?但实际做起来,问题一个接一个。
关键前提:直流注入必须在电机静止、转子锁死或抱闸状态下进行。如果转子在转,反电动势会混进来,算出来的电阻值就全错了。
注入策略
我习惯分两步走:
- 预定位阶段:先通一个较小的直流电流(比如额定电流的10%),把转子拉到固定位置。这一步大概持续100-200ms。
- 测量阶段:加大电流到额定值的20%-30%,等待电流稳定后采样电压和电流。
为什么要预定位?因为PMSM的相电感随转子位置变化。如果转子位置不确定,电感波动会影响电流建立时间,导致你误判稳态到达的时刻。
我的经验:预定位电流不要太大,够用就行。我曾经用30%额定电流做预定位,结果电机抖了一下,机械结构都跟着响。后来改成10%,效果一样好,还安静。
采样时机
电流从零到稳态,时间常数 τ = L/R。对于小电机,τ 可能只有几毫秒;大电机可能几十毫秒。我建议等 5τ 之后再采样,这时候电流误差已经小于1%。
具体做法:
- 注入开始后,连续监测电流变化率 di/dt
- 当 |di/dt| < 阈值(比如 0.1 A/s)时,认为进入稳态
- 连续采样 10 次取平均,降低噪声影响
// 伪代码示例
void dc_injection_resistance_measure(void) {
// 1. 预定位
set_duty_cycle(PRE_POSITION_DUTY);
delay_ms(150);
// 2. 注入测量电流
set_duty_cycle(MEASURE_DUTY);
// 3. 等待稳态
float di_dt = 0;
do {
float i_prev = get_current();
delay_ms(1);
float i_curr = get_current();
di_dt = (i_curr - i_prev) / 0.001;
} while (fabs(di_dt) > 0.1);
// 4. 采样平均
float sum = 0;
for (int k = 0; k < 10; k++) {
sum += get_current();
delay_ms(1);
}
float i_avg = sum / 10.0;
// 5. 计算电阻
float R = V_dc / i_avg;
}
电阻辨识的误差分析与补偿
直流注入法看着简单,但误差来源不少。我整理了一下,主要有这么几类:
| 误差来源 | 影响程度 | 典型偏差 | 补偿方法 |
|---|---|---|---|
| 逆变器管压降 | 大 | 5%-15% | 电压前馈补偿 |
| 死区效应 | 中 | 2%-5% | 死区补偿算法 |
| 采样偏置 | 小 | 1%-3% | 硬件校准/软件偏置消除 |
| 温度变化 | 大 | 10%-40% | 温度模型补偿 |
| 电流未完全稳定 | 中 | 2%-8% | 延长等待时间 |
逆变器管压降补偿
这是最大的坑。你给逆变器发一个占空比,以为加到电机上的电压就是 Vdc × duty,实际上IGBT或MOSFET上有管压降。小电流时管压降占比很大,误差非常明显。
我做过一个实验:给一个24V系统的小电机注入直流,理论计算电阻是0.5Ω,实际测出来0.58Ω,差了16%。查了半天,发现是管压降没补偿。
补偿方法:
- 测量逆变器在不同电流下的管压降特性曲线
- 建立查表或拟合公式:V_comp = f(i)
- 实际加到电机上的电压:V_motor = V_dc × duty - V_comp
注意:管压降是非线性的。小电流时近似恒定,大电流时随电流线性增加。不要用一个固定值去补偿所有工况,否则小电流时欠补,大电流时过补。
死区效应补偿
死区时间是为了防止上下桥臂直通而插入的延迟。但死区会导致实际输出电压与指令电压不一致。对于直流注入这种低压小电流工况,死区效应尤其明显。
我建议的做法:
- 测量死区时间 T_dead 和开关周期 T_sw
- 计算死区引起的电压误差:ΔV = V_dc × T_dead / T_sw
- 根据电流方向修正占空比
// 死区补偿示例
float deadtime_compensation(float duty, float current) {
float delta_duty = T_DEAD / T_SW;
if (current > 0) {
return duty + delta_duty;
} else {
return duty - delta_duty;
}
}
温度补偿
铜绕组的电阻温度系数大约是 0.00393 /°C。也就是说,温度每升高10°C,电阻增加约4%。电机运行到热稳态时,绕组温度可能比环境温度高50-80°C,电阻变化20%-30%很正常。
如果你需要把测量结果折算到标准温度(比如25°C),用这个公式:
R_25 = R_meas / (1 + α × (T_meas - 25))
其中 α = 0.00393,T_meas 是测量时的绕组温度。
我的习惯:在电机里预埋NTC温度传感器,每次做电阻辨识时同时读取温度,把结果统一折算到25°C。这样不同时间测的数据才有可比性。
综合误差补偿流程
把上面这些补偿串起来,完整的电阻辨识流程是这样的:
你看,整个流程走下来,从原始采样到最终输出,中间要过好几道补偿关。我刚开始做的时候,漏了管压降补偿,结果测出来的电阻值拿去算电感,电感参数也跟着偏,整个自整定流程都乱了。
避坑指南:我曾经在一个项目里,电阻辨识结果总是偏大5%左右。查了三天,最后发现是ADC采样偏置没校准。0.1V的偏置在小电压系统里能造成10%的误差。所以,每次做电阻辨识前,先做一次零电流校准,把采样偏置扣掉。
最后说一句,电阻辨识的精度直接影响后续的电感辨识和磁链辨识。电阻错了,后面全错。所以这块值得你多花点心思,把补偿做扎实了。