ICP 点到平面测距算法 OpenCV v4.8.0

本文介绍了用于深度融合管道(如 KinectFusion)的 ICP 算法。

ICP 的目标是对齐两个点云,一个是旧点云(三维模型中的现有点和法线),另一个是新点云(新点和法线,即我们要整合到现有模型中的点和法线)。ICP 返回这两个点云之间的旋转和平移变换。

迭代最近点(ICP)最小化目标函数,即两个点云中相应点之间的点到平面距离(PPD):

E = ∑ i ∣ ∣ p p d ( p i , q i , n i ) ∣ ∣ 2 → 0 E=\sum{_i||ppd\left( p_i,q_i,n_i \right) ||_2\rightarrow 0} E=i∣∣ppd(pi,qi,ni)20

什么是 ppd(p, q, n)?

具体来说,对于每个对应点 PQ,它是点 P 到由点 Q 和位于点 Q 上的法线 N 所决定的平面的距离。

p - 新点云中的第 i 个点

q - 旧点云中的第 i 个点

n - 旧点云中 q 点的法线

因此, ppd(…) 可以表示为(pq 之间的差值)和(n)的点积:
d o t ( T p 2 q ( p ) − q , n ) = d o t ( ( R ⋅ p + t ) − q , n ) = [ ( R ⋅ p + t ) − q ] T ⋅ n dot\left( T_{p2q}\left( p \right) -q,n \right) =dot\left( \left( R\cdot p+t \right) -q,n \right) =\left[ \left( R\cdot p+t \right) -q \right] ^T\cdot n dot(Tp2q(p)q,n)=dot((Rp+t)q,n)=[(Rp+t)q]Tn
是点 p 的刚性变换:
T p 2 q ( p ) = ( R ⋅ p + t ) T_{p2q}\left( p \right) =\left( R\cdot p+t \right) Tp2q(p)=(Rp+t)
T 是我们通过 ICP 搜索的变换,其目的是使每个点 p 与对应点 q 的点到平面距离更近。

如何最小化目标函数?

我们使用高斯-牛顿法进行函数最小化。

在高斯-牛顿法中,我们沿着函数 E 的下降方向,即梯度方向,通过改变 Rt 来完成连续步骤:

  1. 在每一步中,我们将函数 E 线性近似为其当前值加上雅各布矩阵乘以 delta x,后者是由 delta Rdelta t 向量串联而成。
  2. 我们通过求解方程 E_approx(delta_x) = 0 来找到 delta Rdelta t
  3. 我们将 delta Rdelta t 应用于当前的 Rt 变换,然后进行下一次迭代

如何对 E 进行线性化?

让我们在无限小邻域内对其进行近似。

下面是我们要通过改变 Rt 使其最小化的公式:
E = ∑ ∣ ∣ [ ( R ⋅ p + t ) − q ] T ⋅ n ∣ ∣ 2 E=\sum{||\left[ \left( R\cdot p+t \right) -q \right] ^T\cdot n||_2} E=∣∣[(Rp+t)q]Tn2
虽然点到平面的距离与 Rt 都是线性关系,但旋转空间本身并不是线性的。从 R 是如何从旋转角度生成的就可以看出这一点:
R = R z ( γ ) R y ( β ) R x ( α ) = [ cos ⁡ ( γ ) − sin ⁡ ( γ ) 0 sin ⁡ ( γ ) cos ⁡ ( γ ) 0 0 0 1 ] [ cos ⁡ ( β ) 0 sin ⁡ ( β ) 0 1 0 − sin ⁡ ( β ) 0 cos ⁡ ( β ) ] [ 1 0 0 0 cos ⁡ ( α ) − sin ⁡ ( α ) 0 sin ⁡ ( α ) cos ⁡ ( α ) ] R=R_z\left( \gamma \right) R_y\left( \beta \right) R_x\left( \alpha \right) =\left[ \begin{matrix} \cos \left( \gamma \right)& -\sin \left( \gamma \right)& 0\\ \sin \left( \gamma \right)& \cos \left( \gamma \right)& 0\\ 0& 0& 1\\ \end{matrix} \right] \left[ \begin{matrix} \cos \left( \beta \right)& 0& \sin \left( \beta \right)\\ 0& 1& 0\\ -\sin \left( \beta \right)& 0& \cos \left( \beta \right)\\ \end{matrix} \right] \left[ \begin{matrix} 1& 0& 0\\ 0& \cos \left( \alpha \right)& -\sin \left( \alpha \right)\\ 0& \sin \left( \alpha \right)& \cos \left( \alpha \right)\\ \end{matrix} \right] R=Rz(γ)Ry(β)Rx(α)= cos(γ)sin(γ)0sin(γ)cos(γ)0001 cos(β)0sin(β)010sin(β)0cos(β) 1000cos(α)sin(α)0sin(α)cos(α)
但由于我们有无限小的旋转,R 可以用下面的形式近似表示:
R = I + A d θ R=I+Ad\theta R=I+Adθ
其中 I - 单位矩阵,A - 三维特殊正交群 so(3) 的成员。

将所有 sin(t) 和 cos(t) 项逼近其 t -> 0 时的极限,可以得到以下表示:
R = I + [ 0 − γ β γ 0 − α − β α 0 ] = I + s k e w ( [ α β γ ] T ) = I + s k e w ( R s h i f t ) R=I+\left[ \begin{matrix} 0& -\gamma& \beta\\ \gamma& 0& -\alpha\\ -\beta& \alpha& 0\\ \end{matrix} \right] =I+skew\left( \left[ \begin{matrix} \alpha& \beta& \gamma\\ \end{matrix} \right] ^T \right) =I+skew\left( R_{shift} \right) R=I+ 0γβγ0αβα0 =I+skew([αβγ]T)=I+skew(Rshift)
R 的近似值代入 E 的表达式,就得到了:
E a p p r o x = ∑ ∣ ∣ [ ( I + s k e w ( R s h i f t ) ) ⋅ p + t − q ] T ⋅ n ∣ ∣ 2 E_{approx}=\sum{||\left[ \left( I+skew\left( R_{shift} \right) \right) \cdot p+t-q \right] ^T\cdot n||_2} Eapprox=∣∣[(I+skew(Rshift))p+tq]Tn2
E a p p r o x = ∑ ∣ ∣ [ I ⋅ p + s k e w ( R s h i f t ) ⋅ p + t − q ] T ⋅ n ∣ ∣ 2 E_{approx}=\sum{||\left[ I\cdot p+skew\left( R_{shift} \right) \cdot p+t-q \right] ^T\cdot n||_2} Eapprox=∣∣[Ip+skew(Rshift)p+tq]Tn2

E a p p r o x = ∑ ∣ ∣ [ s k e w ( R s h i f t ) ⋅ p + t + p − q ] T ⋅ n ∣ ∣ 2 E_{approx}=\sum{||\left[ skew\left( R_{shift} \right) \cdot p+t+p-q \right] ^T\cdot n||_2} Eapprox=∣∣[skew(Rshift)p+t+pq]Tn2
让我们引入一个近似变换移动的函数 f:
f ( x , p ) = s k e w ( R s h i f t ) ⋅ p + t f\left( x,p \right) =skew\left( R_{shift} \right) \cdot p+t f(x,p)=skew(Rshift)p+t
E a p p r o x = ∑ ∣ ∣ [ f ( x , p ) + p − q ] T ⋅ n ∣ ∣ 2 E_{approx}=\sum{||\left[ f\left( x,p \right) +p-q \right] ^T\cdot n||_2} Eapprox=∣∣[f(x,p)+pq]Tn2

如何最小化 E_approx?

E_approx 的差值(即参数增加的导数)为零时,E_approx 就是最小的:
d ( E a p p r o x ) = ∑ i d ( ∣ ∣ p p d ( T a p p r o x ( p i ) , q i , n i ) ∣ ∣ 2 ) d\left( E_{approx} \right) =\sum{_id\left( ||ppd\left( T_{approx}\left( p_i \right) ,q_i,n_i \right) ||_2 \right)} d(Eapprox)=id(∣∣ppd(Tapprox(pi),qi,ni)2)
∑ i d ( p p d ( T a p p r o x ( p i ) , q i , n i ) 2 ) = ∑ i 2 ⋅ p p d ( . . . ) ⋅ d ( p p d ( T a p p r o x ( p i ) , q i , n i ) ) \sum{_id\left( ppd\left( T_{approx}\left( p_i \right) ,q_i,n_i \right) ^2 \right) =\sum{_i2\cdot ppd\left( ... \right) \cdot d\left( ppd\left( T_{approx}\left( p_i \right) ,q_i,n_i \right) \right)}} id(ppd(Tapprox(pi),qi,ni)2)=i2ppd(...)d(ppd(Tapprox(pi),qi,ni))
让我们微分一下 ppd
d ( p p d ( T a p p r o x ( p i ) , q i , n i ) ) = d ( [ f ( x , p i ) + p i − q i ] T ⋅ n i ) = d f ( x , p i ) T ⋅ n i = d x T f ′ ( x , p i ) T ⋅ n i d\left( ppd\left( T_{approx}\left( p_i \right) ,q_i,n_i \right) \right) =d\left( \left[ f\left( x,p_i \right) +p_i-q_i \right] ^T\cdot n_i \right) =df\left( x,p_i \right) ^T\cdot n_i=dx^Tf'\left( x,p_i \right) ^T\cdot n_i d(ppd(Tapprox(pi),qi,ni))=d([f(x,pi)+piqi]Tni)=df(x,pi)Tni=dxTf(x,pi)Tni
下面是我们从向量 x 中得到的所有变量 x_j 的结果:
∂ E ∂ x j = ∑ [ 2 ⋅ ( f ( x , p ) + p − q ) T ⋅ n ] ⋅ [ f j ′ ( x , p ) T ⋅ n ] = 0 \frac{\partial E}{\partial x_j}=\sum{\left[ 2\cdot \left( f\left( x,p \right) +p-q \right) ^T\cdot n \right] \cdot \left[ f_j'\left( x,p \right) ^T\cdot n \right] =0} xjE=[2(f(x,p)+pq)Tn][fj(x,p)Tn]=0
∑ [ 2 ⋅ n T ⋅ ( f ( x , p ) + p − q ) T ] ⋅ [ n T ⋅ f ′ ( x , p ) ] = 0 \sum{\left[ 2\cdot n^T\cdot \left( f\left( x,p \right) +p-q \right) ^T \right] \cdot \left[ n^T\cdot f'\left( x,p \right) \right] =0} [2nT(f(x,p)+pq)T][nTf(x,p)]=0

让新变量:
Δ p = p − q \varDelta p=p-q Δp=pq
∑ [ 2 ⋅ n T ⋅ ( f ( x , p ) + Δ p ) T ] ⋅ [ n T ⋅ f ′ ( x , p ) ] = 0 \sum{\left[ 2\cdot n^T\cdot \left( f\left( x,p \right) +\varDelta p \right) ^T \right] \cdot \left[ n^T\cdot f'\left( x,p \right) \right] =0} [2nT(f(x,p)+Δp)T][nTf(x,p)]=0
∑ [ ( f ( x , p ) + Δ p ) T ⋅ ( n ⋅ n T ) ] ⋅ f ′ ( x , p ) = 0 \sum{\left[ \left( f\left( x,p \right) +\varDelta p \right) ^T\cdot \left( n·n^T \right) \right] \cdot f'\left( x,p \right) =0} [(f(x,p)+Δp)T(nnT)]f(x,p)=0
∑ f ′ ( x , p ) ⋅ [ n ⋅ n T ] ⋅ ( f ( x , p ) + Δ p ) T = 0 \sum{f'\left( x,p \right) \cdot \left[ n·n^T \right] \cdot \left( f\left( x,p \right) +\varDelta p \right) ^T=0} f(x,p)[nnT](f(x,p)+Δp)T=0
f(x, p) 可以表示为矩阵与向量相乘。要证明这一点,我们必须记住
c r o s s ( a , b ) = s k e w ( a ) ⋅ b = s k e w ( b ) T ⋅ a cross\left( a,b \right) =skew\left( a \right) ·b=skew\left( b \right) ^T\cdot a cross(a,b)=skew(a)b=skew(b)Ta
f ( x , p ) = s k e w ( R s h i f t ) ⋅ p + t s h i f t = s k e w ( p ) T R s h i f t + t s h i f t f\left( x,p \right) =skew\left( R_{shift} \right) \cdot p+t_{shift}=skew\left( p \right) ^TR_{shift}+t_{shift} f(x,p)=skew(Rshift)p+tshift=skew(p)TRshift+tshift
f ( x , p ) = [ s k e w ( p ) T    I 3 × 3 ] ⋅ [ Δ R    Δ t ] T = G ( p ) ⋅ x f\left( x,p \right) =\left[ skew\left( p \right) ^T\ \ I_{3\times 3} \right] \cdot \left[ \varDelta R\ \ \varDelta t \right] ^T=G\left( p \right) \cdot x f(x,p)=[skew(p)T  I3×3][ΔR  Δt]T=G(p)x
引入 G§ 是为了简化计算。

因为 d f ( x , p ) = G ( p ) ⋅ d x = f ′ ( x , p ) ⋅ d x df\left( x,p \right) =G\left( p \right) \cdot dx=f'\left( x,p \right) \cdot dx df(x,p)=G(p)dx=f(x,p)dx
我们得到:
f ′ ( x , p ) = G ( p ) f'\left( x,p \right) =G\left( p \right) f(x,p)=G(p)
∑ f ′ ( x , p ) T ⋅ [ n ⋅ n T ] ⋅ [ f ( x , p ) ] = ∑ f ′ ( x , p ) T ⋅ [ n ⋅ n T ] ⋅ [ − Δ p ] \sum{f'\left( x,p \right) ^T\cdot \left[ n·n^T \right] \cdot \left[ f\left( x,p \right) \right] =}\sum{f'\left( x,p \right) ^T\cdot \left[ n·n^T \right] \cdot \left[ -\varDelta p \right]} f(x,p)T[nnT][f(x,p)]=f(x,p)T[nnT][Δp]
∑ G ( p ) T ⋅ [ n ⋅ n T ] ⋅ [ G ( p ) ⋅ X ] = ∑ G ( p ) T ⋅ [ n ⋅ n T ] ⋅ [ − Δ p ] \sum{G\left( p \right) ^T\cdot \left[ n·n^T \right] \cdot \left[ G\left( p \right) \cdot X \right] =}\sum{G\left( p \right) ^T\cdot \left[ n·n^T \right] \cdot \left[ -\varDelta p \right]} G(p)T[nnT][G(p)X]=G(p)T[nnT][Δp]
让一个新值:
C = G ( p ) T ⋅ n C=G\left( p \right) ^T\cdot n C=G(p)Tn
C T = ( G ( p ) T ⋅ n ) T = n T ⋅ G ( p ) C^T=\left( G\left( p \right) ^T\cdot n \right) ^T=n^T\cdot G\left( p \right) CT=(G(p)Tn)T=nTG(p)
让我们来替换一下:
∑ C ⋅ C T ⋅ X = ∑ C ⋅ n T ⋅ [ − Δ p ] \sum{C\cdot C^T\cdot X=\sum{C\cdot n^T\cdot \left[ -\varDelta p \right]}} CCTX=CnT[Δp]
∑ C ⋅ C T ⋅ [ Δ R Δ t ] = ∑ C ⋅ n T ⋅ [ − Δ p ] \sum{C\cdot C^T\cdot \left[ \begin{array}{c} \varDelta R\\ \varDelta t\\ \end{array} \right] =\sum{C\cdot n^T\cdot \left[ -\varDelta p \right]}} CCT[ΔRΔt]=CnT[Δp]
通过求解这个方程,我们可以得到每次高斯-牛顿迭代的刚性变换位移。

如何应用变换位移?

我们从变换中生成旋转和平移矩阵,然后将当前姿态矩阵乘以我们得到的矩阵。

移位的平移部分会原封不动地加入到生成的矩阵中,而旋转部分的生成则比较麻烦。旋转偏移通过指数化从 so(3) 转换为 SO(3)。事实上,3 乘 1 的 rshift 向量代表旋转轴乘以旋转角度。我们使用罗德里格斯变换从中得到旋转矩阵。更多详情,请参阅维基页面

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值