
1. 混用时钟总伪装成算法问题
仿真定位跳、回放同步器对不齐、TF「偶发」外推——单子常进算法组。打开参数:一半 use_sim_time 为真,一半为假;或回放时只有部分节点跟 /clock。时间轴打架时,任何融合都会显得不稳。习惯:凡「只在回放/仿真复现」或间歇 TF 外推,先打印关键节点的 use_sim_time 与 now(),再谈协方差。定位跳变袋上反复调协方差无效,检查发现定位节点跟 /clock,传感器回放节点用墙钟 stamp——对齐域后,跳变变成可复现的固定模式,算法讨论才有对象。
2. 机制:谁在提供 now()
use_sim_time:=true 时,节点时间来自 /clock;没人发 /clock,时间停滞,定时器与依赖仿真时间的逻辑一起停。权威源应唯一:Gazebo 与 ros2 bag play --clock 不要同时发。真机则全员关闭 sim_time;launch 残留仿真参数按缺陷处理。消息 stamp 表示测量时刻,必须与当时时间域一致。查 TF 用 msg.header.stamp,不要盲目 now()——混用域时,加大 timeout 只会把必现变成更难复现。
ros2 param get /your_node use_sim_time
ros2 topic echo /clock --once3. 三种场景契约
| 模式 | use_sim_time | /clock | 备注 | | 真机 | false | 无 | 传感器 stamp 跟系统/硬件时间 | | 仿真 | true | 仿真器发 | 暂停时应看到依赖逻辑停 | | 回放 | 与播放策略一致 | bag play --clock 时有 | QoS 与录制对齐 |
用顶层 clock_mode:=real|sim|bag 统一注入,子系统只接收。禁止各节点自行猜测。message_filters 对不齐时,先确认两端 stamp 同一域,再调 slop。TF buffer 在 seek/跳变后可能需要清空或重启相关节点。时钟修复不保证算法正确,但保证讨论对象真实。
4. 回放、加速与控制交叉
ros2 bag play --clock 且全员跟随,才是「仿真轴复盘」。部分节点跟墙钟,同步器会随机失败。加速回放(rate>1)适合功能回归,不适合性能验收——截止时间假设会被压缩。步进回放时「实时控制」语义已变,结论要标注倍率。控制拍在错误时间域会「看起来 hz 不对」。分诊:时钟 → 执行器 → 控制器参数。
Nav2 / ros2_control 在仿真下同样跟随仿真时间;混用会导致状态与命令不同步。多机真机靠墙钟同步;仿真多机仍应跟同一 /clock。回放实验记录写明播放命令与倍率,隔月复现靠这条而非口头记忆。
5. 测量钟与 ROS 时间
性能用单调钟;消息与协调走 ROS 时间域。用混用的 now 差值报延迟,会得到漂亮但错误的数字。延迟直方图必须声明时间基。存量迁移:先盘点实际值 → 顶层引入 clock_mode → 删子系统私自设置 → 加摘要与 CI。不要同一周既改时钟又改融合参数——归因会乱。
6. 案例:回放修不好的跳变
定位跳变袋上反复调协方差无效。检查发现定位节点跟 /clock,传感器回放节点用墙钟 stamp。对齐域后,跳变变成可复现的固定模式,算法讨论才有对象。这类单子若直接进算法组,可能白调几周协方差。启动摘要打印关键节点 use_sim_time 与时钟源,能把分诊前置到 bringup 阶段。
7. 验收与门禁
启动摘要打印关键节点 use_sim_time 与时钟源。仿真暂停:依赖仿真时间的定时器应停。真机入口 CI:断言无残留 use_sim_time:=true。回放实验记录写明播放命令与倍率。一场景一时钟域;单一 /clock 权威;stamp 随测量。先让时间诚实,再让估计诚实。
相关
也可以看看
johan's blog