Sim2Sim
本页介绍如何将某个 RL 后端中训练好的策略迁移到 MuJoCo 中回放,以检查该策略在脱离原始训练环境后是否仍然行为正确。
这一步之所以重要,是因为 Isaac Lab 这类训练后端通常对计算设备要求较高。实际使用时,很多用户会在共享服务器或远端 GPU 机器上完成训练,而不是直接在个人电脑上训练。训练完成后,继续留在同一训练环境里做本地校验往往并不方便,因此需要一个基于 MuJoCo 的轻量化 Sim2Sim 工作流,把导出的策略带回本地机器,先完成回放、观察与调试,再进入更复杂的迁移或部署阶段。
这和很多机器人任务里常见的 Sim2Sim 动机略有不同。对那些项目来说,更核心的问题通常是不同仿真引擎对接触动力学的实现存在差异,而 MuJoCo 的接触动力学相对精确,因此常被当作跨引擎回放与校验的主要对象。LAV2 也会受益于这一点,尤其是在接触行为重要的任务里,但这并不是这里最核心的出发点。对本项目而言,更重要的仍然是为“重训练后端上的训练结果”提供一个轻量、本地、方便调试的校验环境。
对 LAV2 来说,实际的 sim-to-sim 路径主要包含三个部分:
- 将训练好的策略导出为可部署的模型文件
- 通过通用 play runner 在 MuJoCo 中运行该策略
- 反复对齐观测、命令与时间尺度,直到迁移后的行为足够可信
sequenceDiagram
autonumber
participant Trainer as 强化学习后端
participant Exporter as 导出器
participant Runner as MuJoCo 回放运行器
participant Policy as 已导出策略
participant Sim as MuJoCo
Trainer->>Exporter: 导出训练后的 checkpoint
Exporter-->>Runner: 加载导出的模型文件
Runner->>Sim: 读取状态与传感器
Runner->>Runner: 重建观测
Runner->>Policy: 执行推理
Policy-->>Runner: 返回归一化动作
Runner->>Runner: 应用映射与命令解释
Runner->>Sim: 用映射后的命令推进回放
Runner->>Runner: 检查时序与行为对齐
1. 导出训练好的策略
第一步是把训练好的策略导出为一种可以脱离原始训练运行时、独立加载的模型格式。
如果训练库本身已经提供 exporter,这一步通常会比较直接:
- 使用
rsl_rl的 Isaac Lab 工作流可以通过其栈内工具导出训练后的策略 - LAV2 的
skrl路径已经在 lav2.runner.skrl.isaaclab 中集成了导出支持
LAV2 的 skrl runner 支持导出 TorchScript(.pt)与 ONNX(.onnx)策略。这些导出文件就是 MuJoCo 侧 play 脚本以及 lav2.runner.skrl.eval 所期待的部署产物。
2. 在 MuJoCo 中回放
拿到导出的策略文件后,下一步就是借助 lav2.runner.common.mujoco 下的通用 play 工具在 MuJoCo 中进行测试。
仓库中已经提供了两个入口脚本:
scripts/sim2sim/LAV2_base_play.pyscripts/sim2sim/LAV2_base_vel_play.py
这两个脚本封装了 MuJoCoPlayConfig、MuJoCoPlayRunner,以及 lav2.runner.skrl.eval 中的策略加载逻辑。
常见用法如下:
uv run python scripts/sim2sim/LAV2_base_play.py --checkpoint /path/to/policy.pt
uv run python scripts/sim2sim/LAV2_base_vel_play.py --checkpoint /path/to/policy.onnx
在这一阶段,MuJoCo 回放并不局限于一种固定命令源。你可以使用:
- 键盘命令
- 手柄命令
- 通过 MuJoCoPlayConfig 中轨迹 hook 指定的轨迹
因此,MuJoCo 回放既可以作为快速的部署前健全性检查,也可以作为更丰富的迁移策略定性测试平台。
回放时最先检查什么
先检查模型是否成功加载、观测维度是否与训练配置一致、策略输出是否有界。然后再检查时间尺度、命令映射以及定性的跟踪行为。
3. 做对齐测试
策略能够在 MuJoCo 中跑起来本身并不够,更关键的是要确保部署侧的假设仍然与训练阶段看到的环境一致。
最重要的对齐项包括:
- 控制频率与 decimation
- 归一化动作映射与命令解释
- 观测构造与通道顺序
控制频率
部署循环必须遵守策略训练时对应的有效动作频率。这既包括 MuJoCoPlayConfig 中 MuJoCo 侧的控制 decimation,也包括训练环境原本对控制更新频率的假设。
如果策略在一种控制频率下训练,却在另一种频率下回放,那么即使模型本身没有问题,也会表现得像“迁移失败”。
归一化与映射
导出模型输出的动作通常仍处于训练环境所使用的归一化空间,因此必须先映射回 MuJoCo 所使用的控制器或执行器空间。
在 LAV2 中,这部分由 lav2.runner.common.mujoco 中的动作与命令逻辑,以及控制器侧的 lav2.controller.mapping 一起完成。
当某个策略数值上看起来稳定,但运动表现明显错误时,这里通常是第一批需要检查的位置。
观测对齐
MuJoCo 回放中构造出的观测必须与训练观测在以下方面保持一致:
- 通道含义
- 通道顺序
- 坐标系约定
- 归一化假设
因此,MuJoCoPlayRunner 中默认的观测提取逻辑非常关键。如果回放观测与训练观测不同,那么这实际上就已经不是在测试同一个任务了。
Sim2Sim 的目标
这一阶段的目标不只是“让策略跑起来”,而是让策略在一个时间尺度、映射与观测都足够接近训练环境的回放栈中运行,从而让结果真正具有解释意义。
在进入更困难的迁移或部署工作之前,这是最低标准。
API 交叉引用
- MuJoCo play 工具:lav2.runner.common.mujoco
- MuJoCo play 配置:MuJoCoPlayConfig
- MuJoCo play runner:MuJoCoPlayRunner
- SKRL Isaac Lab runner 与 exporter 路径:lav2.runner.skrl.isaaclab
- 导出策略加载器:lav2.runner.skrl.eval
- 控制器侧 mapping 辅助:lav2.controller.mapping