VINS-Mono-紧耦合VIO中IMU残差的优化原理和代码解析

前言

VINS-Mono算法中VIO部分是基于优化的方法来做的,其优化的目标函数为:
min ⁡ χ { ∥ r p − H p χ ∥ 2 + ∑ k ∈ B ∥ r B ( z ^ b k + 1 b k , χ ) ∥ P b k + 1 b k 2 + ∑ ( l , j ) ∈ C ρ ( ∥ r C ( z ^ l c j , χ ) ∥ P l c j 2 ) } \min_{\boldsymbol{\chi}} \left\{ {\left\| \mathbf{r}_{p}-\mathbf{H}_{p}\boldsymbol{\chi} \right\|}^{2} + {\sum_{k\in B}\left\| \mathbf{r}_{B}(\hat{\mathbf{z}}_{b_{k+1}}^{b_{k}},\boldsymbol{\chi}) \right\|}_{\mathbf{P}_{b_{k+1}}^{b_{k}}}^{2} + \sum_{(l,j)\in C}\rho(\left\| \mathbf{r}_{C}(\hat{\mathbf{z}}_{l}^{c_{j}},\boldsymbol{\chi}) \right\|^{2}_{\mathbf{P}_{l}^{c_{j}}}) \right\} χminrpHpχ2+kBrB(z^bk+1bk,χ)Pbk+1bk2+(l,j)Cρ(rC(z^lcj,χ)Plcj2)
式中 r B , r C \mathbf{r}_{B},\mathbf{r}_{C} rB,rC分别是相对于IMU和视觉测量的残差项,剩余一项是来自边缘化的先验信息.由于式中每一项残差的定义计算及代码实现的篇幅较大,我将分三篇博客来分析这三个残差项.本篇分析:
∑ k ∈ B ∥ r B ( z ^ b k + 1 b k , χ ) ∥ P b k + 1 b k 2 {\sum_{k\in B}\left\| \mathbf{r}_{B}(\hat{\mathbf{z}}_{b_{k+1}}^{b_{k}},\boldsymbol{\chi}) \right\|}_{\mathbf{P}_{b_{k+1}}^{b_{k}}}^{2} kBrB(z^bk+1bk,χ)Pbk+1bk2

原理

对于非线性最小二乘优化问题,一般都会采用高斯牛顿迭代法将问题转换成如下增量求解的形式:
J T J δ x = − J T f \mathbf{J}^{T}\mathbf{J}\delta \mathbf{x} = -\mathbf{J}^{T}\mathbf{f} JTJδx=JTf
其中 f \mathbf{f} f对应残差方程, J \mathbf{J} J对应残差方程相对于状态量的雅克比矩阵.VINS-Mono中利用的是ceres_solver最小二乘求解库来实现上述计算过程,但需要自己定义残差方程,其次对于复杂问题推荐自己计算雅克比矩阵,这样能够保证优化过程的高效性.

定义残差方程

r B = [ δ α b k + 1 b k δ θ b k + 1 b k δ β b k + 1 b k δ b a δ b g ] 15 × 1 = [ R w b k ( p b k + 1 w − p b k w + 1 2 g w Δ t 2 − v b k w Δ t ) − α ^ b k + 1 b k 2 [ ( γ ^ b k + 1 b k ) − 1 ⊗ q b k w − 1 ⊗ q b k + 1 w ] x y z R w b k ( v b k + 1 w + g w Δ t − v b k w ) − β ^ b k + 1 b k b a b k + 1 − b a b k b w b k + 1 − b w b k ] (1) \mathbf{r}_{B} = \begin{bmatrix} \delta \boldsymbol{\alpha}_{b_{k+1}}^{b_{k}} \\ \delta \boldsymbol{\theta}_{b_{k+1}}^{b_{k}} \\ \delta \boldsymbol{\beta}_{b_{k+1}}^{b_{k}} \\ \delta \mathbf{b}_{a} \\ \delta \mathbf{b}_{g} \end{bmatrix}_{15\times1}= \begin{bmatrix} \mathbf{R}_{w}^{b_{k}}(\mathbf{p}_{b_{k+1}}^{w} - \mathbf{p}_{b_{k}}^{w} + \frac{1}{2}\mathbf{g}^{w}\Delta t^{2} - \mathbf{v}_{b_{k}}^{w}\Delta t) - \hat{\boldsymbol{\alpha}}_{b_{k+1}}^{b_{k}} \\ 2[(\hat{\boldsymbol{\gamma}}_{b_{k+1}}^{b_{k}})^{-1}\otimes{\mathbf{q}_{b_{k}}^{w}}^{-1}\otimes\mathbf{q}_{b_{k+1}}^{w}]_{xyz} \\ \mathbf{R}^{b_{k}}_{w}(\mathbf{v}_{b_{k+1}}^{w} + \mathbf{g}^{w}\Delta t - \mathbf{v}_{b_{k}}^{w}) - \hat{\boldsymbol{\beta}}_{b_{k+1}}^{b_{k}} \\ \mathbf{b}_{a_{b_{k+1}}} - \mathbf{b}_{a_{b_{k}}} \\ \mathbf{b}_{w_{b_{k+1}}} - \mathbf{b}_{w_{b_{k}}} \end{bmatrix} \tag{1} rB=δαbk+1bkδθbk+1bkδβbk+1bkδbaδbg15×1=Rwbk(pbk+1wpbkw+21gwΔt2vbkwΔt)α^bk+1bk2[(γ^bk+1bk)1qbkw1qbk+1w]xyzRwbk(vbk+1w+gwΔtvbkw)β^bk+1bkbabk+1babkbwbk+1bwbk(1)

计算雅克比矩阵

通过公式(1)可以看出参与优化的变量包括 b k b_{k} bk时刻的状态量 [ p b k w , q b k w , v b k w , b a k , b w k ] [\mathbf{p}_{b_{k}}^{w}, \mathbf{q}_{b_{k}}^{w}, \mathbf{v}_{b_{k}}^{w}, \mathbf{b}_{a_{k}}, \mathbf{b}_{w_{k}}] [pbkw,qbkw,vbkw,bak,bwk] b k + 1 b_{k+1} bk+1时刻的状态量 [ p b k + 1 w , q b k + 1 w , v b k + 1 w , b a k + 1 , b w k + 1 ] [\mathbf{p}_{b_{k+1}}^{w}, \mathbf{q}_{b_{k+1}}^{w}, \mathbf{v}_{b_{k+1}}^{w}, \mathbf{b}_{a_{k+1}}, \mathbf{b}_{w_{k+1}}] [pbk+1w,qbk+1w,vbk+1w,bak+1,bwk+1],为了与代码保持一致,我们将这两组状态量分成四组,分别为 [ p b k w , q b k w ] , [ v b k w , b a k , b w k ] , [ p b k + 1 w , q b k + 1 w ] , [ v b k + 1 w , b a k + 1 , b w k + 1 ] [\mathbf{p}_{b_{k}}^{w}, \mathbf{q}_{b_{k}}^{w}], [\mathbf{v}_{b_{k}}^{w}, \mathbf{b}_{a_{k}}, \mathbf{b}_{w_{k}}],[\mathbf{p}_{b_{k+1}}^{w}, \mathbf{q}_{b_{k+1}}^{w}], [\mathbf{v}_{b_{k+1}}^{w}, \mathbf{b}_{a_{k+1}}, \mathbf{b}_{w_{k+1}}] [pbkw,qbkw],[vbkw,bak,bwk],[pbk+1w,qbk+1w],[vbk+1w,bak+1,bwk+1],再分别计算残差方程相对于这四组变量的雅克比矩阵.

相对于 b k b_{k} bk时刻位姿的jacobi
  • 结果
    J [ 0 ] 15 × 7 = ∂ r B ∂ ( p b k w , q b k w ) = [ − R w b k ⌊ R w b k ( p b k + 1 w − p b k w + 1 2 g w Δ t 2 − v b k w Δ t ) ⌋ × 0 − Q + [ q b k + 1 w − 1 ⊗ q b k w ] Q − 1 [ γ b k + 1 b k ] 0 ⌊ R w b k ( v b k + 1 w − v b k w + g w Δ t ) ⌋ × 0 0 0 0 ] (0) \begin{aligned} \mathbf{J}[0]^{15\times7} &= \frac{\partial \mathbf{r}_{B}}{\partial \mathbf{(\mathbf{p}_{b_{k}}^{w}, \mathbf{q}_{b_{k}}^{w})}} = \begin{bmatrix} -\mathbf{R}_{w}^{b_{k}} & \left\lfloor \mathbf{R}_{w}^{b_{k}}(\mathbf{p}_{b_{k+1}}^{w} - \mathbf{p}_{b_{k}}^{w} + \frac{1}{2}\mathbf{g}^{w}\Delta t^{2} - \mathbf{v}_{b_{k}}^{w}\Delta t) \right\rfloor_{\times} \\ \mathbf{0} & -\mathbf{Q}^{+}[{\mathbf{q}_{b_{k+1}}^{w}}^{-1}\otimes\mathbf{q}_{b_{k}}^{w}]\mathbf{Q}^{-1}[\boldsymbol{\gamma}_{b_{k+1}}^{b_{k}}] \\ \mathbf{0} & \left\lfloor \mathbf{R}_{w}^{b_{k}}(\mathbf{v}_{b_{k+1}}^{w}-\mathbf{v}_{b_{k}}^{w}+\mathbf{g}^{w}\Delta t) \right\rfloor_{\times} \\ \mathbf{0} & \mathbf{0} \\ \mathbf{0} & \mathbf{0} \end{bmatrix} \end{aligned} \tag{0} J[0]15×7=(pbkw,qbkw)rB=Rwbk0000Rwbk(pbk+1wpbkw+21gwΔt2vbkwΔt)×Q+[qbk+1w1qbkw]Q1[γbk+1bk]Rwbk(vbk+1wvbkw+gwΔt)×00(0)

  • 推导:
    ∂ δ α b k + 1 b k ∂ q b k w = ∂ [ R w b k ( p b k + 1 w − p b k w + 1 2 g w Δ t 2 − v b k w Δ t ) − α ^ b k + 1 b k ] ∂ q b k w = ∂ [ R w b k p ′ − α ^ b k + 1 b k ] ∂ q b k w = ∂ [ R b k w − 1 p ′ ] ∂ q b k w = [ e x p ( ⌊ δ θ ⌋ × ) R b k w ] − 1 p ′ − R b k w − 1 p ′ δ θ = ( I − ⌊ δ θ ⌋ × ) R w b k p ′ − R w b k p ′ δ θ = − ⌊ δ θ ⌋ × R w b k p ′ δ θ = ⌊ R w b k p ′ ⌋ × δ θ δ θ = ⌊ R w b k p ′ ⌋ × = ⌊ R w b k ( p b k + 1 w − p b k w + 1 2 g w Δ t 2 − v b k w Δ t ) ⌋ × \begin{aligned} \frac{\partial \delta \boldsymbol{\alpha}_{b_{k+1}}^{b_{k}}}{\partial \mathbf{q}_{b_{k}}^{w}} &= \frac{\partial [\mathbf{R}_{w}^{b_{k}}(\mathbf{p}_{b_{k+1}}^{w} - \mathbf{p}_{b_{k}}^{w} + \frac{1}{2}\mathbf{g}^{w}\Delta t^{2} - \mathbf{v}_{b_{k}}^{w}\Delta t) - \hat{\boldsymbol{\alpha}}_{b_{k+1}}^{b_{k}}]}{\partial \mathbf{q}_{b_{k}}^{w}} = \frac{\partial [\mathbf{R}_{w}^{b_{k}}\mathbf{p}' - \hat{\boldsymbol{\alpha}}_{b_{k+1}}^{b_{k}}]}{\partial \mathbf{q}_{b_{k}}^{w}} \\ &= \frac{\partial [{\mathbf{R}_{b_{k}}^{w}}^{-1}\mathbf{p}']}{\partial \mathbf{q}_{b_{k}}^{w}} = \frac{[exp(\left\lfloor \delta \boldsymbol{\theta} \right\rfloor_{\times})\mathbf{R}_{b_{k}}^{w}]^{-1}\mathbf{p}' - {\mathbf{R}_{b_{k}}^{w}}^{-1}\mathbf{p}'}{\delta \boldsymbol{\theta}} \\ &= \frac{(\mathbf{I}-\left\lfloor \delta\boldsymbol{\theta} \right\rfloor_{\times})\mathbf{R}_{w}^{b_{k}}\mathbf{p}' - \mathbf{R}_{w}^{b_{k}}\mathbf{p}'}{\delta \boldsymbol{\theta}} = \frac{-\left\lfloor \delta\boldsymbol{\theta} \right\rfloor_{\times}\mathbf{R}_{w}^{b_{k}}\mathbf{p}'}{\delta \boldsymbol{\theta}}\\ &= \frac{\left\lfloor \mathbf{R}_{w}^{b_{k}}\mathbf{p}' \right\rfloor_{\times}\delta \boldsymbol{\theta}}{\delta \boldsymbol{\theta}} = \left\lfloor \mathbf{R}_{w}^{b_{k}}\mathbf{p}' \right\rfloor_{\times} \\ &= \left\lfloor \mathbf{R}_{w}^{b_{k}}(\mathbf{p}_{b_{k+1}}^{w} - \mathbf{p}_{b_{k}}^{w} + \frac{1}{2}\mathbf{g}^{w}\Delta t^{2} - \mathbf{v}_{b_{k}}^{w}\Delta t) \right\rfloor_{\times} \end{aligned} qbkwδαbk+1bk=qbkw[Rwbk(pbk+1wpbkw+21gwΔt2vbkwΔt)α^bk+1bk]=qbkw[Rwbkpα^bk+1bk]=qbkw[Rbkw1p]=δθ[exp(δθ×)Rbkw]1pRbkw1p=δθ(Iδθ×)RwbkpRwbkp=δθδθ×Rwbkp=δθRwbkp×δθ=Rwbkp×=Rwbk(pbk+1wpbkw+21gwΔt2vbkwΔt)×
    ∂ δ β b k + 1 b k ∂ q b k w \frac{\partial \delta \boldsymbol{\beta}_{b_{k+1}}^{b_{k}}}{\partial \mathbf{q}_{b_{k}}^{w}} qbkwδβbk+1bk的推导与上述推导方法类似,利用左扰动模型进行求导.
    ∂ δ θ b k + 1 b k ∂ q b k w = ∂ ( 2 [ ( γ ^ b k + 1 b k ) − 1 ⊗ q b k w − 1 ⊗ q b k + 1 w ] x y z ) ∂ q b k w = 2 lim ⁡ δ θ b k w → 0 ( γ ^ b k + 1 b k ) − 1 ⊗ ( q b k w ⊗ [ 1 δ θ b k w 2 ] ) − 1 ⊗ q b k + 1 w − ( γ ^ b k + 1 b k ) − 1 ⊗ ( q b k w ) − 1 ⊗ q b k + 1 w δ θ b k w = 2 lim ⁡ δ θ b k w → 0 Q − [ q b k w − 1 ⊗ q b k + 1 w ] Q + [ ( γ ^ b k + 1 b k ) − 1 ] ( [ 0 − δ θ b k w 2 ] ) δ θ b k w = − 2 Q − [ q b k w − 1 ⊗ q b k + 1 w ] Q + [ ( γ ^ b k + 1 b k ) − 1 ] = − 2 Q + [ q b k w − 1 ⊗ q b k + 1 w ] Q − [ γ ^ b k + 1 b k ] \begin{aligned} \frac{\partial \delta \boldsymbol{\theta}_{b_{k+1}}^{b_{k}}}{\partial \mathbf{q}_{b_{k}}^{w}} &= \frac{\partial (2[(\hat{\boldsymbol{\gamma}}_{b_{k+1}}^{b_{k}})^{-1}\otimes{\mathbf{q}_{b_{k}}^{w}}^{-1}\otimes\mathbf{q}_{b_{k+1}}^{w}]_{xyz})}{\partial \mathbf{q}_{b_{k}}^{w}} \\ &= 2\lim_{\delta \boldsymbol{\theta}_{b_{k}}^{w}\rightarrow\mathbf{0}} \frac{({\hat{\boldsymbol{\gamma}}_{b_{k+1}}^{b_{k}}})^{-1}\otimes(\mathbf{q}_{b_{k}}^{w}\otimes\begin{bmatrix} 1 \\ \frac{\delta \boldsymbol{\theta}_{b_{k}}^{w}}{2}\end{bmatrix})^{-1}\otimes\mathbf{q}_{b_{k+1}}^{w} - ({\hat{\boldsymbol{\gamma}}_{b_{k+1}}^{b_{k}}})^{-1}\otimes(\mathbf{q}_{b_{k}}^{w})^{-1}\otimes\mathbf{q}_{b_{k+1}}^{w}}{\delta \boldsymbol{\theta}_{b_{k}}^{w}} \\ &= 2\lim_{\delta \boldsymbol{\theta}_{b_{k}}^{w}\rightarrow\mathbf{0}} \frac{\mathbf{Q}^{-}[{\mathbf{q}_{b_{k}}^{w}}^{-1}\otimes\mathbf{q}_{b_{k+1}}^{w}]\mathbf{Q}^{+}[({\hat{\boldsymbol{\gamma}}_{b_{k+1}}^{b_{k}}})^{-1}](\begin{bmatrix} 0 \\ -\frac{\delta \boldsymbol{\theta}_{b_{k}}^{w}}{2}\end{bmatrix})}{\delta \boldsymbol{\theta}_{b_{k}}^{w}}\\ &= -2\mathbf{Q}^{-}[{\mathbf{q}_{b_{k}}^{w}}^{-1}\otimes\mathbf{q}_{b_{k+1}}^{w}]\mathbf{Q}^{+}[({\hat{\boldsymbol{\gamma}}_{b_{k+1}}^{b_{k}}})^{-1}] \\ &= -2\mathbf{Q}^{+}[{\mathbf{q}_{b_{k}}^{w}}^{-1}\otimes\mathbf{q}_{b_{k+1}}^{w}]\mathbf{Q}^{-}[{\hat{\boldsymbol{\gamma}}_{b_{k+1}}^{b_{k}}}] \end{aligned} qbkwδθbk+1bk=qbkw(2[(γ^bk+1bk)1qbkw1qbk+1w]xyz)=2δθbkw0limδθbkw(γ^bk+1bk)1(qbkw[12δθbkw])1qbk+1w(γ^bk+1bk)1(qbkw)1qbk+1w=2δθbkw0limδθbkwQ[qbkw1qbk+1w]Q+[(γ^bk+1bk)1]([02δθbkw])=2Q[qbkw1qbk+1w]Q+[(γ^bk+1bk)1]=2Q+[qbkw1qbk+1w]Q[γ^bk+1bk]
    上述推导过程中出现的 Q + , Q − \mathbf{Q^{+},Q^{-}} Q+,Q分别为四元素的左乘右乘矩阵,具体求解可参考博客:Quaternion kinematics for ESKF-预测中"一些四元素的性质"章节.

相对于 b k b_{k} bk时刻偏置的jacobi
  • 结果
    J [ 1 ] 15 × 9 = ∂ r B ∂ ( v b k w , b a k , b w k ) = [ − R w b k Δ t − J b a α − J b w α 0 0 − Q + [ q b k + 1 w − 1 ⊗ q b k w ⊗ γ b k + 1 b k ] J b w γ − R w b k − J b a β − J b w β 0 − I 0 0 0 − I ] (1) \mathbf{J}[1]^{15\times9} = \frac{\partial \mathbf{r}_{B}}{\partial (\mathbf{v}_{b_{k}}^{w}, \mathbf{b}_{a_{k}}, \mathbf{b}_{w_{k}})} = \begin{bmatrix} -\mathbf{R}_{w}^{b_{k}}\Delta t & -\mathbf{J}_{\mathbf{b}_{a}}^{\boldsymbol{\alpha}} & -\mathbf{J}_{\mathbf{b}_{w}}^{\boldsymbol{\alpha}} \\ \mathbf{0} & \mathbf{0} & -\mathbf{Q}^{+}[{\mathbf{q}_{b_{k+1}}^{w}}^{-1}\otimes\mathbf{q}_{b_{k}}^{w}\otimes\boldsymbol{\gamma}_{b_{k+1}}^{b_{k}}] \mathbf{J}_{\mathbf{b}_{w}}^{\boldsymbol{\gamma}} \\ -\mathbf{R}_{w}^{b_{k}} & -\mathbf{J}_{\mathbf{b}_{a}}^{\boldsymbol{\beta}} & -\mathbf{J}_{\mathbf{b}_{w}}^{\boldsymbol{\beta}} \\ \mathbf{0} & -\mathbf{I} & \mathbf{0} \\ \mathbf{0} & \mathbf{0} & -\mathbf{I} \end{bmatrix} \tag{1} J[1]15×9=(vbkw,bak,bwk)rB=RwbkΔt0Rwbk00Jbaα0JbaβI0JbwαQ+[qbk+1w1qbkwγbk+1bk]JbwγJbwβ0I(1)
  • 推导
    ∂ δ θ b k + 1 b k ∂ b w k = ∂ ( 2 [ ( γ ^ b k + 1 b k ) − 1 ⊗ q b k w − 1 ⊗ q b k + 1 w ] x y z ) ∂ b w k = 2 lim ⁡ δ b w k → 0 ( γ ^ b k + 1 b k ⊗ [ 1 1 2 J b w γ δ b w k ] ) − 1 ⊗ q b k w − 1 ⊗ q b k + 1 w − ( γ ^ b k + 1 b k ) − 1 ⊗ q b k w − 1 ⊗ q b k + 1 w δ b w k = 2 lim ⁡ δ b w k → 0 [ 1 − 1 2 J b w γ δ b w k ] ⊗ ( γ ^ b k + 1 b k ) − 1 ⊗ q b k w − 1 ⊗ q b k + 1 w − ( γ ^ b k + 1 b k ) − 1 ⊗ q b k w − 1 ⊗ q b k + 1 w δ b w k = 2 lim ⁡ δ b w k → 0 [ 0 − 1 2 J b w γ δ b w k ] ⊗ ( γ ^ b k + 1 b k ) − 1 ⊗ q b k w − 1 ⊗ q b k + 1 w δ b w k = − Q − [ ( γ ^ b k + 1 b k ) − 1 ⊗ q b k w − 1 ⊗ q b k + 1 w ] [ 0 J b w γ ] = − Q + [ ( q b k + 1 w ) − 1 ⊗ q b k w ⊗ γ ^ b k + 1 b k ] [ 0 J b w γ ] \begin{aligned} \frac{\partial \delta \boldsymbol{\theta}_{b_{k+1}}^{b_{k}}}{\partial \mathbf{b}_{w_{k}}} &= \frac{\partial (2[(\hat{\boldsymbol{\gamma}}_{b_{k+1}}^{b_{k}})^{-1}\otimes{\mathbf{q}_{b_{k}}^{w}}^{-1}\otimes\mathbf{q}_{b_{k+1}}^{w}]_{xyz})}{\partial \mathbf{b}_{w_{k}}} \\ &= 2\lim_{\delta \mathbf{b}_{w_{k}}\rightarrow\mathbf{0}}\frac{(\hat{\boldsymbol{\gamma}}_{b_{k+1}}^{b_{k}}\otimes\begin{bmatrix}1\\ \frac{1}{2}{\mathbf{J}_{b_{w}}^{\boldsymbol{\gamma}}\delta\mathbf{b}_{w_{k}}}\end{bmatrix})^{-1}\otimes {\mathbf{q}_{b_{k}}^{w}}^{-1}\otimes\mathbf{q}_{b_{k+1}}^{w}-(\hat{\boldsymbol{\gamma}}_{b_{k+1}}^{b_{k}})^{-1}\otimes {\mathbf{q}_{b_{k}}^{w}}^{-1}\otimes\mathbf{q}_{b_{k+1}}^{w}}{\delta \mathbf{b}_{w_{k}}} \\ &= 2\lim_{\delta \mathbf{b}_{w_{k}}\rightarrow\mathbf{0}}\frac{\begin{bmatrix}1\\ -\frac{1}{2}{\mathbf{J}_{b_{w}}^{\boldsymbol{\gamma}}\delta\mathbf{b}_{w_{k}}}\end{bmatrix}\otimes(\hat{\boldsymbol{\gamma}}_{b_{k+1}}^{b_{k}})^{-1}\otimes {\mathbf{q}_{b_{k}}^{w}}^{-1}\otimes\mathbf{q}_{b_{k+1}}^{w}-(\hat{\boldsymbol{\gamma}}_{b_{k+1}}^{b_{k}})^{-1}\otimes {\mathbf{q}_{b_{k}}^{w}}^{-1}\otimes\mathbf{q}_{b_{k+1}}^{w}}{\delta \mathbf{b}_{w_{k}}} \\ &= 2\lim_{\delta \mathbf{b}_{w_{k}}\rightarrow\mathbf{0}}\frac{\begin{bmatrix}0\\ -\frac{1}{2}{\mathbf{J}_{b_{w}}^{\boldsymbol{\gamma}}\delta\mathbf{b}_{w_{k}}}\end{bmatrix}\otimes(\hat{\boldsymbol{\gamma}}_{b_{k+1}}^{b_{k}})^{-1}\otimes {\mathbf{q}_{b_{k}}^{w}}^{-1}\otimes\mathbf{q}_{b_{k+1}}^{w}}{\delta \mathbf{b}_{w_{k}}}\\ &= -\mathbf{Q}^{-}[(\hat{\boldsymbol{\gamma}}_{b_{k+1}}^{b_{k}})^{-1}\otimes {\mathbf{q}_{b_{k}}^{w}}^{-1}\otimes\mathbf{q}_{b_{k+1}}^{w}]\begin{bmatrix}0 \\ {\mathbf{J}_{b_{w}}^{\boldsymbol{\gamma}}}\end{bmatrix} \\ &= -\mathbf{Q}^{+}[(\mathbf{q}_{b_{k+1}}^{w})^{-1}\otimes \mathbf{q}_{b_{k}}^{w}\otimes \hat{\boldsymbol{\gamma}}_{b_{k+1}}^{b_{k}}]\begin{bmatrix}0 \\ {\mathbf{J}_{b_{w}}^{\boldsymbol{\gamma}}}\end{bmatrix} \end{aligned} bwkδθbk+1bk=bwk(2[(γ^bk+1bk)1qbkw1qbk+1w]xyz)=2δbwk0limδbwk(γ^bk+1bk[121Jbwγδbwk])1qbkw1qbk+1w(γ^bk+1bk)1qbkw1qbk+1w=2δbwk0limδbwk[121Jbwγδbwk](γ^bk+1bk)1qbkw1qbk+1w(γ^bk+1bk)1qbkw1qbk+1w=2δbwk0limδbwk[021Jbwγδbwk](γ^bk+1bk)1qbkw1qbk+1w=Q[(γ^bk+1bk)1qbkw1qbk+1w][0Jbwγ]=Q+[(qbk+1w)1qbkwγ^bk+1bk][0Jbwγ]
  • 说明
    式中 ( J b a α , J b w α , J b a β , J b w β , J b a γ , J b w γ ) (\mathbf{J}_{b_{a}}^{\boldsymbol{\alpha}}, \mathbf{J}_{b_{w}}^{\boldsymbol{\alpha}}, \mathbf{J}_{b_{a}}^{\boldsymbol{\beta}}, \mathbf{J}_{b_{w}}^{\boldsymbol{\beta}}, \mathbf{J}_{b_{a}}^{\boldsymbol{\gamma}}, \mathbf{J}_{b_{w}}^{\boldsymbol{\gamma}}) (Jbaα,Jbwα,Jbaβ,Jbwβ,Jbaγ,Jbwγ)分别为预积分结果相对于偏置的雅克比矩阵,在imu预积分过程中已经计算过了,这里就不需要再计算了.
相对于 b k + 1 b_{k+1} bk+1时刻位姿的jacobi
  • 结果
    J [ 2 ] 15 × 7 = ∂ r B ∂ ( p b k w , q b k w ) = [ R w b k 0 0 Q + [ γ b k + 1 b k − 1 ⊗ q b k w − 1 ⊗ q b k + 1 w ] 0 0 0 0 0 0 ] (2) \mathbf{J}[2]^{15\times7} = \frac{\partial \mathbf{r}_{B}}{\partial \mathbf{(\mathbf{p}_{b_{k}}^{w}, \mathbf{q}_{b_{k}}^{w})}} = \begin{bmatrix} \mathbf{R}_{w}^{b_{k}} & \mathbf{0} \\ \mathbf{0} & \mathbf{Q}^{+}[{\boldsymbol{\gamma}_{b_{k+1}}^{b_{k}}}^{-1}\otimes{\mathbf{q}_{b_{k}}^{w}}^{-1}\otimes\mathbf{q}_{b_{k+1}}^{w}] \\ \mathbf{0} & \mathbf{0} \\ \mathbf{0} & \mathbf{0} \\ \mathbf{0} & \mathbf{0} \end{bmatrix} \tag{2} J[2]15×7=(pbkw,qbkw)rB=Rwbk00000Q+[γbk+1bk1qbkw1qbk+1w]000(2)
  • 推导
    ∂ δ θ b k + 1 b k ∂ q b k + 1 w = ∂ ( 2 [ ( γ ^ b k + 1 b k ) − 1 ⊗ q b k w − 1 ⊗ q b k + 1 w ] x y z ) ∂ q b k + 1 w = 2 [ ( γ ^ b k + 1 b k ) − 1 ⊗ q b k w − 1 ⊗ q b k + 1 w ⊗ [ 1 1 2 δ θ b k + 1 w ] ] − 2 [ ( γ ^ b k + 1 b k ) − 1 ⊗ q b k w − 1 ⊗ q b k + 1 w ] δ θ b k + 1 w = ( γ ^ b k + 1 b k ) − 1 ⊗ q b k w − 1 ⊗ q b k + 1 w ⊗ [ 0 δ θ b k + 1 w ] δ θ b k + 1 w = Q + [ ( γ ^ b k + 1 b k ) − 1 ⊗ q b k w − 1 ⊗ q b k + 1 w ] \begin{aligned} \frac{\partial \delta\boldsymbol{\theta}_{b_{k+1}}^{b_{k}}}{\partial \mathbf{q}_{b_{k+1}}^{w}} &= \frac{\partial (2[(\hat{\boldsymbol{\gamma}}_{b_{k+1}}^{b_{k}})^{-1}\otimes{\mathbf{q}_{b_{k}}^{w}}^{-1}\otimes\mathbf{q}_{b_{k+1}}^{w}]_{xyz})}{\partial \mathbf{q}_{b_{k+1}}^{w}} \\ &= \frac{2[(\hat{\boldsymbol{\gamma}}_{b_{k+1}}^{b_{k}})^{-1}\otimes{\mathbf{q}_{b_{k}}^{w}}^{-1}\otimes\mathbf{q}_{b_{k+1}}^{w}\otimes\begin{bmatrix}1\\ \frac{1}{2}\delta\boldsymbol{\theta}_{b_{k+1}}^{w}\end{bmatrix}] - 2[(\hat{\boldsymbol{\gamma}}_{b_{k+1}}^{b_{k}})^{-1}\otimes{\mathbf{q}_{b_{k}}^{w}}^{-1}\otimes\mathbf{q}_{b_{k+1}}^{w}]}{\delta \boldsymbol{\theta}_{b_{k+1}}^{w}} \\ &= \frac{(\hat{\boldsymbol{\gamma}}_{b_{k+1}}^{b_{k}})^{-1}\otimes{\mathbf{q}_{b_{k}}^{w}}^{-1}\otimes\mathbf{q}_{b_{k+1}}^{w}\otimes\begin{bmatrix} 0 \\ \delta\boldsymbol{\theta}_{b_{k+1}}^{w} \end{bmatrix}}{\delta \boldsymbol{\theta}_{b_{k+1}}^{w}} \\ &=\mathbf{Q}^{+}[(\hat{\boldsymbol{\gamma}}_{b_{k+1}}^{b_{k}})^{-1}\otimes{\mathbf{q}_{b_{k}}^{w}}^{-1}\otimes\mathbf{q}_{b_{k+1}}^{w}] \end{aligned} qbk+1wδθbk+1bk=qbk+1w(2[(γ^bk+1bk)1qbkw1qbk+1w]xyz)=δθbk+1w2[(γ^bk+1bk)1qbkw1qbk+1w[121δθbk+1w]]2[(γ^bk+1bk)1qbkw1qbk+1w]=δθbk+1w(γ^bk+1bk)1qbkw1qbk+1w[0δθbk+1w]=Q+[(γ^bk+1bk)1qbkw1qbk+1w]
相对于 b k + 1 b_{k+1} bk+1时刻偏置的jacobi
  • 结果
    J [ 3 ] 15 × 9 = ∂ r B ∂ ( v b k + 1 w , b a k + 1 , b w k + 1 ) = [ 0 0 0 0 0 0 R w b k 0 0 0 I 0 0 0 I ] (3) \mathbf{J}[3]^{15\times9} = \frac{\partial \mathbf{r}_{B}}{\partial (\mathbf{v}_{b_{k+1}}^{w}, \mathbf{b}_{a_{k+1}}, \mathbf{b}_{w_{k+1}})} = \begin{bmatrix} \mathbf{0} & \mathbf{0} & \mathbf{0} \\ \mathbf{0} & \mathbf{0} & \mathbf{0} \\ \mathbf{R}_{w}^{b_{k}} & \mathbf{0} & \mathbf{0} \\ \mathbf{0} & \mathbf{I} & \mathbf{0} \\ \mathbf{0} & \mathbf{0} & \mathbf{I} \end{bmatrix} \tag{3} J[3]15×9=(vbk+1w,bak+1,bwk+1)rB=00Rwbk00000I00000I(3)

代码解析

    virtual bool Evaluate(double const *const *parameters, double *residuals, double **jacobians) const
    {

        // 第i帧位姿信息p_b(i)_w, q_b_(i)_w
        Eigen::Vector3d Pi(parameters[0][0], parameters[0][1], parameters[0][2]);
        Eigen::Quaterniond Qi(parameters[0][6], parameters[0][3], parameters[0][4], parameters[0][5]);
		// 第i帧偏置信息v_b(i)_w, b_a(i), b_w(i)
        Eigen::Vector3d Vi(parameters[1][0], parameters[1][1], parameters[1][2]);
        Eigen::Vector3d Bai(parameters[1][3], parameters[1][4], parameters[1][5]);
        Eigen::Vector3d Bgi(parameters[1][6], parameters[1][7], parameters[1][8]);

        // 第i帧位姿信息p_b(j)_w, q_b_(j)_w
        Eigen::Vector3d Pj(parameters[2][0], parameters[2][1], parameters[2][2]);
        Eigen::Quaterniond Qj(parameters[2][6], parameters[2][3], parameters[2][4], parameters[2][5]);
		// 第i帧偏置信息v_b(j)_w, b_a(j), b_w(j)
        Eigen::Vector3d Vj(parameters[3][0], parameters[3][1], parameters[3][2]);
        Eigen::Vector3d Baj(parameters[3][3], parameters[3][4], parameters[3][5]);
        Eigen::Vector3d Bgj(parameters[3][6], parameters[3][7], parameters[3][8]);

        // 计算第i帧与第j帧之间的状态残差
        Eigen::Map<Eigen::Matrix<double, 15, 1>> residual(residuals);
        residual = pre_integration->evaluate(Pi, Qi, Vi, Bai, Bgi,
                                             Pj, Qj, Vj, Baj, Bgj);

        // 计算用马氏距离表示的残差
        Eigen::Matrix<double, 15, 15> sqrt_info = Eigen::LLT<Eigen::Matrix<double, 15, 15>>(pre_integration->covariance.inverse()).matrixL().transpose();
        //sqrt_info.setIdentity();
        residual = sqrt_info * residual;

        if (jacobians)
        {
            double sum_dt = pre_integration->sum_dt;
            // 获取imu预积分过程中计算的位置相对于偏置状态的雅克比矩阵
            Eigen::Matrix3d dp_dba = pre_integration->jacobian.template block<3, 3>(O_P, O_BA);
            Eigen::Matrix3d dp_dbg = pre_integration->jacobian.template block<3, 3>(O_P, O_BG);
			// 获取imu预积分过程中计算的姿态相对于偏置的雅克比矩阵
            Eigen::Matrix3d dq_dbg = pre_integration->jacobian.template block<3, 3>(O_R, O_BG);
			// 获取imu预积分过程中计算的速度相对于偏置的雅克比矩阵
            Eigen::Matrix3d dv_dba = pre_integration->jacobian.template block<3, 3>(O_V, O_BA);
            Eigen::Matrix3d dv_dbg = pre_integration->jacobian.template block<3, 3>(O_V, O_BG);

            if (pre_integration->jacobian.maxCoeff() > 1e8 || pre_integration->jacobian.minCoeff() < -1e8)
            {
                ROS_WARN("numerical unstable in preintegration");
                //std::cout << pre_integration->jacobian << std::endl;
                ///                ROS_BREAK();
            }

			// 对应公式(0)
            if (jacobians[0])
            {
                Eigen::Map<Eigen::Matrix<double, 15, 7, Eigen::RowMajor>> jacobian_pose_i(jacobians[0]);
                jacobian_pose_i.setZero();

                jacobian_pose_i.block<3, 3>(O_P, O_P) = -Qi.inverse().toRotationMatrix();
                jacobian_pose_i.block<3, 3>(O_P, O_R) = Utility::skewSymmetric(Qi.inverse() * (0.5 * G * sum_dt * sum_dt + Pj - Pi - Vi * sum_dt));

#if 0
            jacobian_pose_i.block<3, 3>(O_R, O_R) = -(Qj.inverse() * Qi).toRotationMatrix();
#else
                Eigen::Quaterniond corrected_delta_q = pre_integration->delta_q * Utility::deltaQ(dq_dbg * (Bgi - pre_integration->linearized_bg));
                jacobian_pose_i.block<3, 3>(O_R, O_R) = -(Utility::Qleft(Qj.inverse() * Qi) * Utility::Qright(corrected_delta_q)).bottomRightCorner<3, 3>();
#endif

                jacobian_pose_i.block<3, 3>(O_V, O_R) = Utility::skewSymmetric(Qi.inverse() * (G * sum_dt + Vj - Vi));

                jacobian_pose_i = sqrt_info * jacobian_pose_i;

                if (jacobian_pose_i.maxCoeff() > 1e8 || jacobian_pose_i.minCoeff() < -1e8)
                {
                    ROS_WARN("numerical unstable in preintegration");
                    //std::cout << sqrt_info << std::endl;
                    //ROS_BREAK();
                }
            }
            // 对应公式(1)
            if (jacobians[1])
            {
                Eigen::Map<Eigen::Matrix<double, 15, 9, Eigen::RowMajor>> jacobian_speedbias_i(jacobians[1]);
                jacobian_speedbias_i.setZero();
                jacobian_speedbias_i.block<3, 3>(O_P, O_V - O_V) = -Qi.inverse().toRotationMatrix() * sum_dt;
                jacobian_speedbias_i.block<3, 3>(O_P, O_BA - O_V) = -dp_dba;
                jacobian_speedbias_i.block<3, 3>(O_P, O_BG - O_V) = -dp_dbg;

#if 0
            jacobian_speedbias_i.block<3, 3>(O_R, O_BG - O_V) = -dq_dbg;
#else
                //Eigen::Quaterniond corrected_delta_q = pre_integration->delta_q * Utility::deltaQ(dq_dbg * (Bgi - pre_integration->linearized_bg));
                //jacobian_speedbias_i.block<3, 3>(O_R, O_BG - O_V) = -Utility::Qleft(Qj.inverse() * Qi * corrected_delta_q).bottomRightCorner<3, 3>() * dq_dbg;
                jacobian_speedbias_i.block<3, 3>(O_R, O_BG - O_V) = -Utility::Qleft(Qj.inverse() * Qi * pre_integration->delta_q).bottomRightCorner<3, 3>() * dq_dbg;
#endif

                jacobian_speedbias_i.block<3, 3>(O_V, O_V - O_V) = -Qi.inverse().toRotationMatrix();
                jacobian_speedbias_i.block<3, 3>(O_V, O_BA - O_V) = -dv_dba;
                jacobian_speedbias_i.block<3, 3>(O_V, O_BG - O_V) = -dv_dbg;

                jacobian_speedbias_i.block<3, 3>(O_BA, O_BA - O_V) = -Eigen::Matrix3d::Identity();

                jacobian_speedbias_i.block<3, 3>(O_BG, O_BG - O_V) = -Eigen::Matrix3d::Identity();

                jacobian_speedbias_i = sqrt_info * jacobian_speedbias_i;

                //ROS_ASSERT(fabs(jacobian_speedbias_i.maxCoeff()) < 1e8);
                //ROS_ASSERT(fabs(jacobian_speedbias_i.minCoeff()) < 1e8);
            }
            // 对应公式(3)
            if (jacobians[2])
            {
                Eigen::Map<Eigen::Matrix<double, 15, 7, Eigen::RowMajor>> jacobian_pose_j(jacobians[2]);
                jacobian_pose_j.setZero();

                jacobian_pose_j.block<3, 3>(O_P, O_P) = Qi.inverse().toRotationMatrix();

#if 0
            jacobian_pose_j.block<3, 3>(O_R, O_R) = Eigen::Matrix3d::Identity();
#else
                Eigen::Quaterniond corrected_delta_q = pre_integration->delta_q * Utility::deltaQ(dq_dbg * (Bgi - pre_integration->linearized_bg));
                jacobian_pose_j.block<3, 3>(O_R, O_R) = Utility::Qleft(corrected_delta_q.inverse() * Qi.inverse() * Qj).bottomRightCorner<3, 3>();
#endif

                jacobian_pose_j = sqrt_info * jacobian_pose_j;

                //ROS_ASSERT(fabs(jacobian_pose_j.maxCoeff()) < 1e8);
                //ROS_ASSERT(fabs(jacobian_pose_j.minCoeff()) < 1e8);
            }
            // 对应公式(4)
            if (jacobians[3])
            {
                Eigen::Map<Eigen::Matrix<double, 15, 9, Eigen::RowMajor>> jacobian_speedbias_j(jacobians[3]);
                jacobian_speedbias_j.setZero();

                jacobian_speedbias_j.block<3, 3>(O_V, O_V - O_V) = Qi.inverse().toRotationMatrix();

                jacobian_speedbias_j.block<3, 3>(O_BA, O_BA - O_V) = Eigen::Matrix3d::Identity();

                jacobian_speedbias_j.block<3, 3>(O_BG, O_BG - O_V) = Eigen::Matrix3d::Identity();

                jacobian_speedbias_j = sqrt_info * jacobian_speedbias_j;

                //ROS_ASSERT(fabs(jacobian_speedbias_j.maxCoeff()) < 1e8);
                //ROS_ASSERT(fabs(jacobian_speedbias_j.minCoeff()) < 1e8);
            }
        }

        return true;
    }

参考

https://github.com/StevenCui/VIO-Doc
https://github.com/HKUST-Aerial-Robotics/VINS-Mono

注释代码路径

https://github.com/chennuo0125-HIT/vins-note

  • 2
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值