「机器人抓不到杯子」· 假设清单

2026-09-07 夜 ~ 09-08 凌晨 · 15 次实机试跑 + 4 个模型的离线视觉测试 · 全部 0 成功
★ 结论:state 泄漏 ★ 模型的输入里含着正在运动的那条手臂的关节角,而训练目标就是「预测下一步关节角」—— state ↔ action 相关系数 0.99,把当前角度原样抄一遍误差只有 0.9°。 捷径几乎白送,模型就不学看图了。

决定性证据:2×2 单变量对照

模型E(数据翻几遍)state 含正在动的臂?pan 斜率相关 r会看图?
smolvla_1502 b21.64❌ 不含(左臂不动)+0.210+0.565会
a100-600019.74❌ 不含(左臂不动)+0.214+0.417会
b16 right-pick19.4✅ 含(全 17 维)+0.004+0.013不会
sep3-left93.5✅ 含(左臂正在动)+0.006+0.313不会
中间两行:E 几乎相同(19.4 vs 19.74),只差 state → 斜率差 50 倍。
上面两行:state 同样不含任务臂,E 差 12 倍 → 斜率几乎相同(0.210 vs 0.214)。
→ E 不是原因,state 才是。「斜率」= 杯子挪 1°,模型输出跟着挪几度;示范里应接近 +1。

全部假设一览

#假设状态依据
1state 泄漏:输入含正在动的臂,模型抄 state 不看图 成立(主因) 上面的 2×2;state↔action r=0.99,照抄误差 0.9°;四个模型无一例外
2E 太高(数据翻太多遍导致过拟合) 排除 E=19.74 与 E=19.4 斜率差 50 倍;E=1.64 与 E=19.74 斜率几乎相同。E 与看不看图无关
3state[6] 被截断(17 维砍成 6 维)是 bug 排除 唯一成功过的模型正是 state[6]。它恰好截掉了正在动的臂,是这个「bug」救了它
4rename_map 把相机改名导致图像进不去 排除 键名不匹配时 lerobot 会 raise ValueError,从没报过;empty_cameras=0 也不会偷偷补零。成功那个模型同样 rename 了
5decay_steps=30000 ≠ steps=20000 导致学习率没降完 排除 optim/schedulers.py:149 会自动把曲线缩放到 steps,S=1.0。30000 是官方默认值
6安全层把动作拦住了 排除 15 次里 14 次 safety layer cut 0%,策略想动多少就动多少(743°、886°、1722° 全部执行)
7内存不足导致推理抖动、闭环太慢 排除 释放 3G 内存后慢帧中位 278ms,落在原区间 148~414ms 内,没变
8换 checkpoint(训练步数不同)能改善 排除 006000(28 ep)比 020000(93.5 ep)更差,cycles 2→5 恶化
9夹爪换过,标定值不对导致空抓 排除 0820 / 0826 / sep3 三个数据集(跨越换爪)夹住杯子都是 28 左右,标定一致
10爪上贴的黄标签干扰视觉 排除 拿掉后 cycles 仍是 2,照样失败
11相机被占 / 预览抢设备影响试跑 排除 是我的预览服务造成的,改成读 /dev/shm 共享帧后 8770 恢复正常
12示范阶段性不清晰(elbow 来回摆,不是单调下降) 未排除 三个数据集干净下降 0/40、0/54、0/50,下降帧占比都只有 39~42%。真实存在,但解释不了模型之间的差异
13杯位超出训练分布 未排除 今晚杯子始终在画面中央,对右臂偏远;训练集右臂抓取 pan 中位 −22.6°。没测过分布最密的位置
14桌面那块透明塑料膜干扰 未排除 训练集桌面是干净的,膜是新增的反光物,一直没拿掉
15数据量不够(40~54 集不足以学会视觉定位) 未排除 会看图的两个模型斜率也只有 +0.21,离示范的 +1 差 5 倍——看得见但不够准

四种失败模式(今晚实机观察到的)

模型动作幅度夹爪开合病症
sep3-left (b64)5.9~9.1 °/s2~5走同一条固定轨迹,六次重合到 1.7~3.7°
b16 right8.4~11.2 °/s6~10输出噪声大,方向偶然对
smolvla b211~12 °/s5~9够得到,抓不准(手伸到位,合爪抓空)
a100-600028 °/s1动作最猛,唯一顶到安全边界(cut 5%),一次连续抓取但仍空抓
ACT1.0 °/s0几乎不动,60 秒总共只动 60°

官方对 state 泄漏的配方(存在,但 SmolVLA 用不了)

class RelativeActionsProcessorStep:
    """Converts absolute actions to relative actions (action -= state)...
       Mirrors OpenPI's DeltaActions transform."""
途径可用?
use_relative_actions(训练目标改成增量)pi0 / pi05 / pi0_fast / groot 有
SmolVLA 的 use_delta_joint_actions_aloha一开就 raise NotImplementedError
数据集层面转换 recompute_stats(relative_action=True)存在,要改数据管线
把任务臂的 state 拿掉(今晚验证有效的那条)右臂任务直接可用;左臂要重排维度
★ 截断永远取前 6 维 = 左臂。所以「不传 --policy.input_features=null 让它截断」这招 只对右臂任务有效;左臂任务要用,必须重排数据集里 state 的维度顺序,推理侧也得同步改。

下一步(按性价比排)

做什么成本为什么
杯子挪到训练集最密的位置 + 拿掉塑料膜零假设 13、14 还没排除,而且不花任何代价
训一批「右臂 + 不传 input_features=null」租 GPU 1~2h主动利用 state 截断,而不是碰运气
左臂数据集重排 state 维度写脚本 + 改推理侧让左臂也能用这招;要先等右臂验证
补「接近—下降—合爪」阶段清晰的示范录制时间假设 12、15;会看图的模型斜率也只有 +0.21,说明还不够准
今晚我归因错了六次 内存 · checkpoint 步数 · rename_map · decay_steps · gripper over-range 误读 · E 假设。 每次都是先下结论再去查证。最后那个 2×2 之所以能定案,是因为它是单变量的—— 这也是今晚唯一一次先设计对照再看结果。