# RTK–IMU 多源原始数据与旋转标定 V3

## 可行性结论

重构方向正确且必要。原始捕获中确实存在旧导出链路忽略的 BESTNAVA、
PVTSLNA 和 HI13 姿态/四元数。它们可以补充速度、质量、绝对姿态和静止
重力约束，但本批数据尚不能通过完整旋转门禁：

- BESTNAVA 约 0.8–1 Hz，严格高速样本很少。
- 当前动态主要是平面 yaw，R1b 的两个倾斜自由度仍弱可观。
- HI13 四元数与 GNSS 真北存在稳定但非机械的 yaw 偏差，可能来自磁偏角或
  内部导航融合。
- 两个明确水平静止会话的 R2G 很稳定，但它是水平/重力先验约束解。

因此，本次重构显著提高了诊断能力，也防止错误外参进入平移；它没有把信息
不足包装成“标定成功”。

## 三批原始数据

扫描根目录：

- 0808：D:\data\raw_serial_capture_v2，仅选 20260808。
- 0815：D:\data\0815\raw_serial_capture_v2；目录实际包含 20260812–14。
- 0819：D:\data\0819\raw_serial_capture_v2。

按文件名捕获开始时间在 1.5 s 内一一配对：

| 批次 | G90/HI13 配对 | GNHPR | BESTNAVA | PVTSLNA | Q4 HPR | Fixed Doppler |
|---|---:|---:|---:|---:|---:|---:|
| 0808 | 18 | 46,180 | 8,291 | 5,993 | 45,606 | 8,128 |
| 0815 | 28 | 96,241 | 12,660 | 9,638 | 27,045 | 3,385 |
| 0819 | 9 | 15,717 | 2,029 | 1,427 | 14,976 | 1,930 |

共完成 55 组统一导出。0815 有一组 G90 没有匹配 HI13，manifest 将其列为
unmatched。发现一条 NMEA 时间为 0913A：保留原始行，设备时间留空并隔离，
没有回退到 host receive time。

速度不等于高速激励。增加速度 ≥1.5 m/s、水平速度标准差 ≤0.25 m/s 后，
三个批次分别只剩 44、8、0 条候选。

## 统一导出

输出根目录：D:\data\rtk_imu_unified_v3。

每组捕获：

- imu.npz：HI13 system_time、gyro、accel、RPY、WXYZ quaternion、磁场、
  PPS stamp、温度、气压和 host receive UTC。
- rtk.csv：每条原生异步 GGA/GNHPR/BESTNAVA/PVTSLNA 单独成行，不再把
  HPR/BEST/PVT 最近邻挂到 GGA。
- export_summary.json：原始捕获摘要、报文数量、四元数范数和设备到 host
  的仿射时钟诊断。
- manifest.json：全部会话、批次、目录和 unmatched 记录。

时间规则：

1. HI13 system_time 是 IMU 主时间轴。
2. BESTNAVA/PVTSLNA 使用 GNSS week/TOW 和 leap seconds。
3. GGA/GNHPR 使用报文自己的 UTC time-of-day。
4. RTK GNSS 测量时刻通过 HI13 device→host 仿射模型映射进 HI13 设备时钟。
5. host receive time 只用于跨时钟桥接、延迟和抖动诊断，绝不替代采样时刻。
6. checksum 无效、时间畸形或非固定解记录保留，但不进入求解。

## 新旋转链路

### R1b：基线在 IMU 中的 2DoF 方向

对连续 Q4 GNHPR 基线和 HI13 陀螺相对旋转使用不变量：

    angle(b_ENU(t0), b_ENU(t1))
      = angle(b_IMU, DeltaR_IMU b_IMU)

估计 b_IMU 的两个倾斜自由度及逐会话陀螺零偏。安装信息只用于选择 +X
半球，并施加明确记录的弱 20° 先验。按会话等权，输出残差、协方差和信息
奇异值。

### R2V：基线 + Doppler velocity

筛选条件：

- BESTNAVA position 为 SOL_COMPUTED/NARROW_INT；
- velocity 为 SOL_COMPUTED/DOPPLER_VELOCITY；
- checksum 有效；
- 水平速度 ≥1.5 m/s、速度标准差 ≤0.25 m/s；
- |IMU gyro_z| ≤3°/s；
- 速度方向与横向基线接近正交；
- GNHPR Q4，并有时间邻近的合法 HI13 quaternion。

基线给车右，Doppler velocity 给车前，叉积给车上。HI13 quaternion 的
body/world 和 ENU/NED 候选全部评分，只保留残差最小者。该方法会把 HI13
导航 yaw 偏差带入候选，因此必须和 R2G 交叉验证。

### R2G：基线 + 水平静止重力

只允许调用方明确标记的水平静止会话。本次使用：

- 0819_20260819_072130（flat_static_hdg207）
- 0819_20260819_073045（flat_static_hdg082）

每 10 s 分块，要求 gyro norm ≤0.35°/s，且加速度模长距标准重力不超过
0.15 m/s²。R1b 提供车右，加速度中值提供车上，叉积得到车前。

### R3：稳定性与正式门禁

R2V/R2G 都输出：

- 样本和会话数量；
- SO(3) RMS/P95；
- 旋转向量样本标准差和均值协方差；
- leave-one-session；
- 10 样本或 10 s block-out。

只有 R1b 可观、R2V 和 R2G 各自稳定、二者差异 ≤2° 时，才将
translation_unlocked 设为 true。旧 GNHPR 三轴手眼不参与正式门禁。

## 首轮实测

R1b：

    b_IMU = [0.999999976, -0.000213959, -0.000044368]
    tilt_yz = [-0.0123, -0.0025] deg
    pairs = 2091
    RMS / P95 = 0.8086 / 1.7105 deg
    information singular values = [1.176e-2, 8.476e-4]
    std = [27.77, 7.47] deg
    gate = failed

点估计接近 +X 是安装先验与名义轴一致的结果；巨大协方差说明不能宣称
数据独立估出了这两个小角。

R2V：

    qualifying samples / sessions = 41 / 2
    selected quaternion convention = HI13_q_body_to_ENU
    RPY = [0.7532, 0.0708, -9.2944] deg
    RMS / P95 = 1.8436 / 3.4975 deg
    max leave-one-session = 3.4519 deg
    gate = failed

R2G：

    level-static blocks / sessions = 53 / 2
    RPY = [0.4543, -0.0026, 0.0122] deg
    RMS / P95 = 0.2542 / 0.2732 deg
    max leave-one-session = 0.2688 deg
    gate = passed (level/gravity-prior constrained)

R2V 与 R2G 的 SO(3) 差异为 9.3119°。R3 最终：

    full_rotation_accepted = false
    translation_unlocked = false

## 下一轮数据要求

1. BESTNAVA 改为至少 10 Hz，并确认 Doppler velocity 与 GNHPR 使用同一
   GNSS week/TOW 输出周期。
2. 每个日期都录制多段 ≥3 m/s、持续 20–30 s 的正向直线；包含不同方位，
   避免单一磁环境和单一会话支配。
3. 为 R1b 增加可控的 roll/pitch 激励；只有平面 yaw 无法稳定估出横向
   基线的两个微小倾斜角。
4. 每个日期至少录两种车头方位的明确水平静止段，检验 HI13 重力和绝对
   quaternion 的跨日期稳定性。
5. 若 HI13 quaternion 的 yaw 来自磁融合，应获取其导航坐标定义、磁偏角
   设置和融合状态；否则 R2V 只使用其 roll/pitch，yaw 由 GNSS 基线和速度
   决定。
6. 上述门禁通过前继续冻结杆臂和平移。

## 实现入口

- tools/rscap_v2/g90_rtk.py：GGA/GNHPR/BESTNAVA/PVTSLNA 和双 checksum。
- tools/rscap_v2/hi13_imu.py：HI91 system_time、惯性、姿态和四元数。
- tools/export_rtk_imu_unified.py：55 组配对、原生异步导出和断点续导。
- rtk_imu/rtk_imu_multisource.py：R1b/R2V/R2G/R3。
- tools/run_rtk_imu_multisource.py：多源旋转命令行入口。
- artifacts/rtk_imu_calibration_v3/multisource_result.json：首轮 R3 结果。
