补充data4与data5联合标定流程并显式配置RTK高度

This commit is contained in:
lichun.qu
2026-07-28 15:36:00 +08:00
parent e847cd4590
commit 24eaa8508e
9 changed files with 289 additions and 20 deletions
+2 -1
View File
@@ -9,6 +9,7 @@
| `prepare_multisensor_dataset.ps1` | 每站选一帧,生成yaw-only RTK参考轨迹和`frames_all` |
| `run_direct_rtk_lidar.ps1` | 从combined数据运行RTK直接标定和最终结果封装 |
| `run_single_dataset.ps1` | 执行地面、两个GICP后端、精筛、共识和AX=XB求解 |
| `run_joint_rtk_lidar.ps1` | 合并多个独立批次的批内共识运动对和地面平面,求解共享外参 |
| `view_result.ps1` | 打开3D运动对对比并打印数值增量 |
所有路径均为命令行参数;默认生成目录`work/``outputs/`不会提交Git。
所有路径均为命令行参数。标定入口要求显式传入RTK/GGA参考点离地高度,避免静默使用与实车不符的默认值;默认生成目录`work/``outputs/`不会提交Git。
+1 -1
View File
@@ -1,8 +1,8 @@
param(
[Parameter(Mandatory = $true)][string]$CombinedRoot,
[Parameter(Mandatory = $true)][double]$RtkReferenceHeightAboveGroundM,
[string]$OutputRoot = "",
[string]$WorkRoot = "",
[double]$RtkReferenceHeightAboveGroundM = 0.8535,
[int]$ExpectedStations = 34,
[int]$MinPairs = 20,
[int]$Bootstrap = 200
+1 -1
View File
@@ -4,8 +4,8 @@
[Parameter(Mandatory = $true)][string]$ImuCapture,
[Parameter(Mandatory = $true)][string]$OutputRoot,
[string]$LidarObject = "frontlidar",
[Parameter(Mandatory = $true)][double]$RtkReferenceHeightAboveGroundM,
[string]$Timezone = "+08:00",
[double]$RtkReferenceHeightAboveGroundM = 0.8535,
[int]$ExpectedStations = 34,
[int]$MinPairs = 20,
[int]$Bootstrap = 200
+103
View File
@@ -0,0 +1,103 @@
param(
[Parameter(Mandatory = $true)][string[]]$BatchNames,
[Parameter(Mandatory = $true)][string[]]$Pairs,
[Parameter(Mandatory = $true)][string[]]$GroundPlanes,
[Parameter(Mandatory = $true)][string]$OutputRoot,
[Parameter(Mandatory = $true)][double]$RtkReferenceHeightAboveGroundM,
[int]$Bootstrap = 200,
[double]$MaxBatchTranslationDifferenceM = 0.25,
[double]$MaxBatchRotationDifferenceDeg = 5.0
)
$ErrorActionPreference = "Stop"
$Repo = Split-Path -Parent $PSScriptRoot
if ($BatchNames.Count -lt 2) {
throw "At least two independent batches are required"
}
if (($Pairs.Count -ne $BatchNames.Count) -or ($GroundPlanes.Count -ne $BatchNames.Count)) {
throw "BatchNames, Pairs, and GroundPlanes must have the same number of entries"
}
if ($RtkReferenceHeightAboveGroundM -le 0.0) {
throw "RtkReferenceHeightAboveGroundM must be greater than zero"
}
foreach ($Path in @($Pairs + $GroundPlanes)) {
if (-not (Test-Path -LiteralPath $Path)) {
throw "Input does not exist: $Path"
}
}
$PreflightRoot = Join-Path $OutputRoot "preflight"
New-Item -ItemType Directory -Force -Path $PreflightRoot | Out-Null
$BatchExtrinsics = @()
for ($Index = 0; $Index -lt $BatchNames.Count; $Index++) {
$SafeName = $BatchNames[$Index] -replace '[^A-Za-z0-9_.-]', '_'
$BatchExtrinsic = Join-Path $PreflightRoot "$SafeName.json"
Write-Host "[preflight batch: $($BatchNames[$Index])]"
& python (Join-Path $Repo "code\rigorous_calibration.py") calibrate `
--pairs $Pairs[$Index] `
--ground-planes $GroundPlanes[$Index] `
--reference-height $RtkReferenceHeightAboveGroundM `
--bootstrap 0 `
--output $BatchExtrinsic | Out-Null
if ($LASTEXITCODE -ne 0) { throw "Batch preflight failed: $($BatchNames[$Index])" }
$BatchExtrinsics += $BatchExtrinsic
}
for ($Index = 1; $Index -lt $BatchNames.Count; $Index++) {
$SafeName = $BatchNames[$Index] -replace '[^A-Za-z0-9_.-]', '_'
$ComparisonPath = Join-Path $PreflightRoot "$SafeName-vs-batch0.json"
& python (Join-Path $Repo "code\compare_extrinsics.py") `
--reference $BatchExtrinsics[0] `
--candidate $BatchExtrinsics[$Index] `
--output $ComparisonPath | Out-Null
if ($LASTEXITCODE -ne 0) { throw "Batch comparison failed: $($BatchNames[$Index])" }
$Comparison = Get-Content -LiteralPath $ComparisonPath -Raw | ConvertFrom-Json
$TranslationDifference = [double]$Comparison.relative_translation_norm_m
$RotationDifference = [double]$Comparison.relative_rotation_deg
Write-Host ("[preflight consistency] {0} vs {1}: {2:F4} m / {3:F3} deg" -f `
$BatchNames[$Index], $BatchNames[0], $TranslationDifference, $RotationDifference)
if (($TranslationDifference -gt $MaxBatchTranslationDifferenceM) -or
($RotationDifference -gt $MaxBatchRotationDifferenceDeg)) {
throw ("Batch extrinsics are inconsistent: {0} vs {1} = {2:F4} m / {3:F3} deg; " +
"check RTK heading/frame convention and sensor installation") -f `
$BatchNames[$Index], $BatchNames[0], $TranslationDifference, $RotationDifference
}
}
$InputRoot = Join-Path $OutputRoot "inputs"
$JointPairs = Join-Path $InputRoot "joint_consensus_pairs.npz"
$JointGroundPlanes = Join-Path $InputRoot "joint_ground_planes.csv"
$InputSummary = Join-Path $InputRoot "joint_input_summary.json"
$Extrinsic = Join-Path $OutputRoot "shared_T_RTK_lidar.json"
$BuildArgs = @((Join-Path $Repo "code\build_joint_rtk_lidar_inputs.py"))
for ($Index = 0; $Index -lt $BatchNames.Count; $Index++) {
$BuildArgs += @(
"--batch-name", $BatchNames[$Index],
"--pairs", $Pairs[$Index],
"--ground-planes", $GroundPlanes[$Index]
)
}
$BuildArgs += @(
"--output-pairs", $JointPairs,
"--output-ground-planes", $JointGroundPlanes,
"--summary", $InputSummary
)
Write-Host "[combine independent batches]"
& python @BuildArgs
if ($LASTEXITCODE -ne 0) { throw "Combining independent batches failed" }
Write-Host "[solve shared T_RTK_lidar]"
& python (Join-Path $Repo "code\rigorous_calibration.py") calibrate `
--pairs $JointPairs `
--ground-planes $JointGroundPlanes `
--reference-height $RtkReferenceHeightAboveGroundM `
--bootstrap $Bootstrap `
--output $Extrinsic
if ($LASTEXITCODE -ne 0) { throw "Shared RTK-LiDAR calibration failed" }
Write-Host "Shared T_RTK_lidar: $Extrinsic"
Write-Host "Joint input summary: $InputSummary"
+1 -1
View File
@@ -1,8 +1,8 @@
param(
[Parameter(Mandatory = $true)][string]$Prepared,
[Parameter(Mandatory = $true)][string]$OutputRoot,
[Parameter(Mandatory = $true)][double]$ReferenceHeight,
[string]$ReferencePoseFile = "reference_poses_rtk_gga_raw_heading.csv",
[double]$ReferenceHeight = 0.8535,
[int]$MinPairs = 20,
[int]$Bootstrap = 100
)