4. 控制周期与实时性:控制频率的选择,RTOS任务优先级配置,通信延迟对抖动的影响

聊到人形机器人的抖动,很多人第一反应是PID参数没调好。但说实话,我见过太多案例——PID参数已经调到极限了,机器人还是抖。这时候你该怀疑什么?

我建议你先看看控制周期和实时性。这两个东西,才是决定控制质量的地基。地基不稳,上面盖多漂亮的PID算法都没用。

4.1 控制频率怎么选?不是越快越好

很多人有个误区:控制频率越高,控制效果越好。其实不是这样。你想想看,频率太高,系统反而会出问题。

核心原则:控制频率至少要高于系统机械谐振频率的2倍,但不要超过传感器更新率的1/2。

我在项目中遇到过一台双足机器人,走路时髋关节一直抖。一开始我以为是电机齿槽转矩的问题,折腾了两天。后来一查,控制频率设了2kHz,但IMU的更新率只有500Hz。说白了,控制器在拿过时的数据做决策,不抖才怪。

具体怎么选?我一般按这个流程来:

  1. 摸清机械谐振频率——用手推一下关节,或者扫频测试,找到第一个谐振峰
  2. 确定传感器更新率——编码器、IMU、力矩传感器,取最慢的那个
  3. 选控制频率——在谐振频率×2 和 传感器更新率÷2 之间取一个值
  4. 留余量——实际用的时候,再降20%左右,给系统留点喘气的空间
关节类型 典型谐振频率 推荐控制频率 传感器限制
髋关节(大惯量) 15-25 Hz 500-800 Hz 编码器 1kHz
膝关节(中惯量) 25-40 Hz 800-1000 Hz 编码器 1kHz
踝关节(小惯量) 40-60 Hz 1000-1500 Hz IMU 500Hz
手臂末端 10-20 Hz 400-600 Hz 力矩传感器 500Hz

我的小技巧:如果你不确定谐振频率,可以先设一个保守值(比如500Hz),然后边跑边往上提。当抖动突然变大的那一刻,你就知道临界点在哪了。

4.2 RTOS任务优先级配置——别让控制任务饿死

控制频率选好了,接下来就是怎么在RTOS里把它跑稳。我见过太多人,代码写得挺好,但任务优先级配得一塌糊涂。

举个例子。有一次我帮朋友调试一个机器人,控制周期总是忽长忽短。查了半天,发现他把通信任务优先级设得比控制任务还高。结果每次收发数据时,控制任务就被抢占了。嗯,这能不抖吗?

我个人习惯这样配优先级:

  • 最高优先级:电流环/力矩环(1kHz以上,必须实时响应)
  • 次高优先级:位置环/速度环(控制任务本体)
  • 中等优先级:状态估计(IMU融合、关节状态更新)
  • 低优先级:通信任务(CAN、EtherCAT、串口)
  • 最低优先级:日志、调试、人机交互

注意:千万不要把控制任务和通信任务放在同一个优先级。我曾经吃过这个亏——两个任务同优先级,RTOS轮转调度,控制周期直接翻倍。

这里给一个FreeRTOS的配置示例,我常用的:

// 任务优先级定义
#define PRIO_CURRENT_LOOP   5   // 电流环,最高
#define PRIO_POSITION_LOOP  4   // 位置环
#define PRIO_STATE_ESTIMATE 3   // 状态估计
#define PRIO_CAN_COMM       2   // CAN通信
#define PRIO_LOGGING        1   // 日志

// 任务创建
xTaskCreate(currentLoopTask, "CurrentLoop", 256, NULL, PRIO_CURRENT_LOOP, NULL);
xTaskCreate(positionLoopTask, "PosLoop", 512, NULL, PRIO_POSITION_LOOP, NULL);
xTaskCreate(stateEstimateTask, "StateEst", 512, NULL, PRIO_STATE_ESTIMATE, NULL);
xTaskCreate(canCommTask, "CANComm", 256, NULL, PRIO_CAN_COMM, NULL);
xTaskCreate(loggingTask, "Logging", 128, NULL, PRIO_LOGGING, NULL);

还有一个容易被忽略的点——中断优先级。控制任务用的定时器中断,优先级一定要高于其他外设中断。不然定时器一响,结果被CAN中断抢了,控制周期就歪了。

4.3 通信延迟——看不见的抖动源

这个坑我踩过好几次。通信延迟,说白了就是数据从传感器到控制器、再从控制器到执行器,路上花了多少时间。这个时间如果不稳定,抖动就来了。

我举个例子。你用的是CAN总线,理论速率1Mbps。但实际跑起来,总线负载一高,帧的发送延迟就会波动。这个波动反映到控制上,就是周期抖动。

常见的通信方式及其延迟特性:

通信方式 典型延迟 抖动 适用场景
EtherCAT < 100 μs < 1 μs 高端人形机器人
CAN FD 100-500 μs 10-50 μs 中端机器人
普通CAN 200-1000 μs 50-200 μs 低端/教育机器人
RS485/Modbus 1-5 ms 0.5-2 ms 不推荐用于实时控制
WiFi/UDP 1-10 ms 1-5 ms 仅用于远程监控

关键指标:通信延迟的值不是最可怕的,可怕的是抖动。一个稳定的500μs延迟,比一个波动在100-500μs之间的延迟好得多。

怎么降低通信延迟的影响?我总结了几条经验:

  • 用同步模式——EtherCAT的DC模式、CAN的同步帧,都能让所有节点在同一时刻采样
  • 减少总线负载——能合并的数据帧就合并,别一帧只传一个字节
  • 数据预处理——在传感器端做滤波,别把原始噪声全扔到总线上
  • 时间戳补偿——每个数据包带上时间戳,控制器可以根据延迟做插值

避坑指南:我曾经在CAN总线上同时跑了电机控制和传感器数据,结果总线负载到了80%。控制周期从1ms抖到了1.8ms。后来我把传感器数据改成每5ms发一次,问题就解决了。说白了,别让非实时数据挤占实时数据的带宽。

4.4 知识体系总览

下面这张图,把控制周期、RTOS优先级、通信延迟这三者的关系串起来了。你可以把它当作调试时的检查清单。

控制周期与实时性知识体系 控制频率选择 机械谐振频率 传感器更新率 留20%余量 扫频测试确认 RTOS优先级配置 电流环 > 位置环 状态估计 > 通信 避免同优先级 中断优先级更高 通信延迟管理 选择低抖动总线 使用同步模式 降低总线负载 时间戳补偿 三者共同决定:控制周期抖动 任何一环出问题,都会在机器人运动上表现为抖动 调试检查流程 ① 用逻辑分析仪抓控制任务的实际执行间隔 ② 检查是否有高优先级任务频繁抢占 ③ 测量通信总线的帧间隔抖动 ④ 对比实际控制周期与设定值,偏差超过10%就要排查

你看,这三件事其实是环环相扣的。控制频率选得再好,RTOS优先级配乱了也没用;RTOS配得再合理,通信延迟一抖,全白搭。我每次调试新机器人,都会按这个流程走一遍,基本能解决80%的抖动问题。

最后提醒一句:别一上来就调PID。先拿示波器或者逻辑分析仪,看看你的控制周期到底稳不稳。如果周期本身就在抖,调PID就是白费力气。我见过太多人在这上面浪费了一两周时间。