解读《视觉SLAM十四讲》,带你一步一步入门视觉SLAM—— 第 4 讲 李群与李代数 (下)

2024-06-05 17:38

本文主要是介绍解读《视觉SLAM十四讲》,带你一步一步入门视觉SLAM—— 第 4 讲 李群与李代数 (下),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

在上一篇解读中《解读《视觉SLAM十四讲》,带你一步一步入门视觉SLAM—— 第 4 讲 李群与李代数 (上)》,我们先介绍了李群的定义,知道了我们前面介绍的旋转矩阵集合就是一个李群,然后我们通过一些推导得到了 R = e x p ( ϕ ∧ ) R = exp(\boldsymbol\phi^{\wedge}) R=exp(ϕ),知道了旋转矩阵可以用李代数(向量)的形式去表示。
  
  这一讲我将带你解读李群和李代数的指数和对数运算,以及李代数的求导与扰动模型。

解读

指数映射与对数映射

前面我们经过不懈的努力找到了旋转矩阵另外的表示方法, R = e x p ( ϕ ∧ ) R = exp(\boldsymbol\phi^{\wedge}) R=exp(ϕ),但是我们并不知道这个 e x p ( ϕ ∧ ) exp(\boldsymbol\phi^{\wedge}) exp(ϕ)应该怎么计算。下面我们就跟着作者的思路一起学习一下。
  
  我要再次跟你强调一下 ϕ \boldsymbol\phi ϕ是一个四元数,它实际上也是一个三维向量,这一点请你别忘记了!同时你也别忘记 ϕ ∧ \boldsymbol\phi^{\wedge} ϕ表示的是反对称矩阵,虽然前面已经说过了,但是再强调一下。
  首先我们对 e x p ( ϕ ∧ ) exp(\boldsymbol\phi^{\wedge}) exp(ϕ)写成泰勒级数的方式: e x p ( ϕ ∧ ) = ∑ n = 0 ∞ 1 n ! ( ϕ ∧ ) n (0) exp(\boldsymbol\phi^{\wedge})=\sum_{n=0}^{\infty} \frac 1 {n!}(\boldsymbol\phi^{\wedge})^n\tag 0 exp(ϕ)=n=0n!1(ϕ)n(0)因为 ϕ \boldsymbol\phi ϕ是一个向量,我们可以把它写成 ϕ = θ a ⃗ \boldsymbol\phi=\theta\vec a ϕ=θa a ⃗ \vec a a 是和 ϕ \boldsymbol\phi ϕ方向相同的单位向量, θ \theta θ ϕ \boldsymbol\phi ϕ的模长。
  书中说到,对于 a ⃗ \vec a a ,有两条性质, a ⃗ ∧ ∗ a ⃗ ∧ = a ⃗ ∗ a ⃗ T − I (1) \vec a^{\wedge}*\vec a^{\wedge} = \vec a * \vec a^T - I \tag1 a a =a a TI(1) a ⃗ ∧ ∗ a ⃗ ∧ ∗ a ⃗ ∧ = − a ⃗ ∧ (2) \vec a^{\wedge}*\vec a^{\wedge}*\vec a^{\wedge} = -\vec a^{\wedge} \tag2 a a a =a (2)然后我们就可以把(0)式进行展开了,并且应用上(1)(2)的性质 e x p ( ϕ ∧ ) = e x p ( θ a ⃗ ∧ ) = ∑ n = 0 ∞ 1 n ! ( θ a ⃗ ∧ ) n (3) exp(\boldsymbol\phi^{\wedge})=exp(\theta\vec a^{\wedge})=\sum_{n=0}^{\infty} \frac 1 {n!}(\theta\vec a^{\wedge})^n \tag3 exp(ϕ)=exp(θa )=n=0n!1(θa )n(3)上式(3)拆开之后进行化简(具体过程请看书本),可以得到如下式子: e x p ( ϕ ∧ ) = e x p ( θ a ⃗ ∧ ) = c o s θ I + ( 1 − c o s θ ) a ⃗ a ⃗ T + s i n θ a ⃗ ∧ (4) exp(\boldsymbol\phi^{\wedge})=exp(\theta\vec a^{\wedge})=cos\theta I+(1-cos\theta)\vec a\vec a^T+sin\theta\vec a^{\wedge}\tag4 exp(ϕ)=exp(θa )=cosθI+(1cosθ)a a T+sinθa (4)握草,(4)式不就是我们第三讲说的罗德里格斯公式吗!?怎么搞了一大圈又回到原点了!?
  
  我们上面的推导没有问题啊!那我们来仔细回味一下这些推导过程到底得到了什么结论。我们首先把旋转矩阵转换成了对应的李代数形式,即就是 R = e x p ( ϕ ∧ ) R = exp(\boldsymbol\phi^{\wedge}) R=exp(ϕ),然后求得了这个指数映射关系实际上就是罗德里格斯公式。我们上一讲运用罗德里格斯公式的时候,主要是用来把旋转向量转换成旋转矩阵。我们仔细观察(4)式, θ a ⃗ \theta\vec a θa 不就等于是旋转向量嘛!那是不是可以这样认为,旋转矩阵对应的李代数实际上就是旋转向量组成的空间?答案是:肯定的!
  
  上面的思维转换有一点难,我们不妨再不厌其烦的总结一下:我们一开始从 R = e x p ( ϕ ∧ ) R = exp(\boldsymbol\phi^{\wedge}) R=exp(ϕ)入手,等式左边的 R R R是李群,等式右边的 ϕ \boldsymbol\phi ϕ是它对应的李代数,然后去探索这个指数映射的解法。惊奇的发现这个指数映射其实就是通过罗德里格斯公式变换过去的。而罗德里格斯公式也是将旋转向量转换成旋转矩阵的公式。所以我们可以得出一个结论,旋转矩阵群对应的李代数,实际上就是旋转向量组成的集合。也就是说旋转矩阵的李代数就是旋转向量。哇,看来前面这么多内容只是将第三讲的内容升华到了更高的理论层上,实际上也并没有什么新的东西产生。于是乎,我们得到了一个结论,第四讲一大部分东西都是忽悠人的,现在看来确实是这样的,哈哈,开个玩笑。
  
  当我们明白了旋转矩阵的指数映射之后,理解变换矩阵 T T T的指数映射似乎也就顺理成章了,所以不再解读,大家看书即可!如果上面的内容你还觉得思维转不过来,请结合书本多看几遍。
  
  既然有旋转向量到旋转矩阵的指数映射,那也就有旋转矩阵到旋转向量的对数映射,书中直接给出了对数映射的公式,大家请参考课本《十四讲》!

BCH公式与近似形式

还记得我们一开始说的,为什么要引入李群和李代数吗?目的就是为了后面在优化过程中就行求导。
  
  我们说旋转矩阵不满足加法封闭,那我们通过指数映射 R = e x p ( ϕ ∧ ) R = exp(\boldsymbol\phi^{\wedge}) R=exp(ϕ)变换到李代数的形式,在李代数的形式下,我们是否可以求导呢?让我们来探讨一下:
  
  如果我们想要能求导,那就必须能够对加法运算封闭,如果我们旋转矩阵相乘对应到李代数是相加,那我们就可以通过李代数的方式进行求导。也就是说要下式(5)成立 e x p ( ϕ 1 ∧ ) e x p ( ϕ 2 ∧ ) = e x p ( ϕ 1 ∧ + ϕ 2 ∧ ) (5) exp(\boldsymbol\phi_1^{\wedge})exp(\boldsymbol\phi_2^{\wedge})=exp(\boldsymbol\phi_1^{\wedge}+\boldsymbol\phi_2^{\wedge})\tag5 exp(ϕ1)exp(ϕ2)=exp(ϕ1+ϕ2)(5) l n ( e x p ( ϕ 1 ∧ ) e x p ( ϕ 2 ∧ ) ) = ϕ 1 ∧ + ϕ 2 ∧ (6) ln(exp(\boldsymbol\phi_1^{\wedge})exp(\boldsymbol\phi_2^{\wedge}))=\boldsymbol\phi_1^{\wedge}+\boldsymbol\phi_2^{\wedge}\tag6 ln(exp(ϕ1)exp(ϕ2))=ϕ1+ϕ2(6)显然对于标量,(5)(6)式是成立的,但是对于矩阵(5)(6)式不成立。
  等式(6)在对矩阵进行运算的时候,是满足 BCH公式, l n ( e x p ( ϕ 1 ∧ ) e x p ( ϕ 2 ∧ ) ) = ϕ 1 ∧ + ϕ 2 ∧ + 1 2 [ ϕ 1 ∧ , [ ϕ 1 ∧ , ϕ 2 ∧ ] ] + . . . ln(exp(\boldsymbol\phi_1^{\wedge})exp(\boldsymbol\phi_2^{\wedge}))=\boldsymbol\phi_1^{\wedge}+\boldsymbol\phi_2^{\wedge}+\frac 1 2[\boldsymbol\phi_1^{\wedge},[\boldsymbol\phi_1^{\wedge},\boldsymbol\phi_2^{\wedge}]]+... ln(exp(ϕ1)exp(ϕ2))=ϕ1+ϕ2+21[ϕ1,[ϕ1,ϕ2]]+...,BCH告诉我们,在做矩阵运算时会产生余项。
  考虑到,SLAM是实际问题,所以我们可以做一些近似,我们把小量中二次以上的项都忽略掉。此时(6)式可以近似等于如下表达: l n ( e x p ( ϕ 1 ∧ ) e x p ( ϕ 2 ∧ ) ) ∨ ≈ { J l ( ϕ 2 ) − 1 ϕ 1 + ϕ 2 当 ϕ 1 为 小 量 J r ( ϕ 1 ) − 1 ϕ 2 + ϕ 1 当 ϕ 2 为 小 量 (7) ln(exp(\boldsymbol\phi_1^{\wedge})exp(\boldsymbol\phi_2^{\wedge}))^{\vee}\approx \begin{cases}J_l(\boldsymbol\phi_2)^{-1}\boldsymbol\phi_1+\boldsymbol\phi_2 当\boldsymbol\phi_1为小量\\J_r(\boldsymbol\phi_1)^{-1}\boldsymbol\phi_2+\boldsymbol\phi_1 当\boldsymbol\phi_2为小量\end{cases}\tag 7 ln(exp(ϕ1)exp(ϕ2)){Jl(ϕ2)1ϕ1+ϕ2 ϕ1Jr(ϕ1)1ϕ2+ϕ1 ϕ(7)通过(7)式我们就可以得到,李群乘法(旋转矩阵乘法)与李代数加法(旋转向量)的关系了。
  现在我们来考虑一个实际情况,某一个旋转 R R ,对应的李代数 ϕ \boldsymbol\phi ϕ,如果在它左边乘上一个微小的旋转 Δ R \Delta R ΔR Δ R \Delta R ΔR对应的李代数是 Δ ϕ \Delta\boldsymbol\phi Δϕ。根据(7)式中的第一个等式,可以得到: e x p ( Δ ϕ ) e x p ( ϕ ) = e x p ( ( ϕ + J l − 1 Δ ϕ ) ∧ ) (8) exp(\Delta\boldsymbol\phi)exp(\boldsymbol\phi)=exp((\boldsymbol\phi+J_l^{-1}\Delta\boldsymbol\phi)^{\wedge})\tag8 exp(Δϕ)exp(ϕ)=exp((ϕ+Jl1Δϕ))(8)上式(8)就告诉我们了,旋转向量加法和旋转矩阵乘法的关系。注意:我并没有介绍 J J J怎么计算,请看书中给出的公式。
  反过来,当我们做李代数的加法时,对应到李群上面是怎样的运算呢?可以由下式给出: e x p ( ( ϕ + Δ ϕ ) ∧ ) = e x p ( ( J l − 1 Δ ϕ ) ∧ ) e x p ( ϕ ∧ ) = e x p ( ϕ ∧ ) e x p ( ( J r − 1 Δ ϕ ) ∧ ) (9) exp((\boldsymbol\phi+\Delta\boldsymbol\phi)^{\wedge})=exp((J_l^{-1}\Delta\boldsymbol\phi)^{\wedge})exp(\boldsymbol\phi^{\wedge})=exp(\boldsymbol\phi^{\wedge})exp((J_r^{-1}\Delta\boldsymbol\phi)^{\wedge})\tag{9} exp((ϕ+Δϕ))=exp((Jl1Δϕ))exp(ϕ)=exp(ϕ)exp((Jr1Δϕ))(9)

对位姿有关函数的求导问题

对于旋转矩阵和变换矩阵,它们对加法都没有良好的定义,所以对姿态有关的函数求导,只能通过李代数进行。关于用李代数解决求导问题,有两种思路:

  • 用李代数表示姿态,然后根据李代数加法对李代数进行求导;
  • 对李群左乘或者右乘微小扰动,然后对该扰动求导。

我们分别来看这两种求导方法的区别:

李代数的求导

假设我们要对前后两个时刻的姿态求导数,因为旋转矩阵没有加法,所以我们就对旋转矩阵的李代数就行求导,如下式: ∂ ( e x p ( ϕ ∧ ) ) ∂ ϕ (10) \frac {\partial(exp(\boldsymbol\phi^{\wedge}))}{\partial\boldsymbol\phi}\tag{10} ϕ(exp(ϕ))(10)上式根据导数定义进行求导: ∂ ( e x p ( ϕ ∧ ) ) ∂ ϕ = lim ⁡ δ ϕ → 0 e x p ( ( ϕ + δ ϕ ) ∧ ) − e x p ( ϕ ∧ ) δ ϕ \frac{\partial(exp(\boldsymbol\phi^{\wedge}))}{\partial\boldsymbol\phi} = \lim_{\delta\boldsymbol\phi \to 0}\frac{exp((\boldsymbol\phi+\delta\boldsymbol\phi)^{\wedge})-exp(\boldsymbol\phi^{\wedge})}{\delta\boldsymbol\phi} ϕ(exp(ϕ))=δϕ0limδϕexp((ϕ+δϕ))exp(ϕ)对上式使用BCH线性近似,得到: = lim ⁡ δ ϕ → 0 e x p ( ( J l δ ϕ ) ∧ ) e x p ( ϕ ∧ ) − e x p ( ϕ ∧ ) δ ϕ =\lim_{\delta\boldsymbol\phi \to 0}\frac{exp((J_l\delta\boldsymbol\phi)^{\wedge})exp(\boldsymbol\phi^{\wedge})-exp(\boldsymbol\phi^{\wedge})}{\delta\boldsymbol\phi} =δϕ0limδϕexp((Jlδϕ))exp(ϕ)exp(ϕ)对上式的 e x p ( ( J l δ ϕ ) ∧ ) exp((J_l\delta\boldsymbol\phi)^{\wedge}) exp((Jlδϕ))进行泰勒展开取常数项和一次项,得到下式: ≈ lim ⁡ δ ϕ → 0 e x p ( I + ( J l δ ϕ ) ∧ ) e x p ( ϕ ∧ ) − e x p ( ϕ ∧ ) δ ϕ \approx\lim_{\delta\boldsymbol\phi \to 0}\frac{exp(I+(J_l\delta\boldsymbol\phi)^{\wedge})exp(\boldsymbol\phi^{\wedge})-exp(\boldsymbol\phi^{\wedge})}{\delta\boldsymbol\phi} δϕ0limδϕexp(I+(Jlδϕ))exp(ϕ)exp(ϕ) = lim ⁡ δ ϕ → 0 ( J l δ ϕ ) ∧ e x p ( ϕ ∧ ) δ ϕ =\lim_{\delta\boldsymbol\phi \to 0}\frac{(J_l\delta\boldsymbol\phi)^{\wedge}exp(\boldsymbol\phi^{\wedge})}{\delta\boldsymbol\phi} =δϕ0limδϕ(Jlδϕ)exp(ϕ)上式中,将反对称符号看做是叉积,交换两项的叉积顺序,然后变号: = lim ⁡ δ ϕ → 0 − ( e x p ( ϕ ∧ ) ) ∧ J l δ ϕ δ ϕ =\lim_{\delta\boldsymbol\phi \to 0}\frac{-(exp(\boldsymbol\phi^{\wedge}))^{\wedge}J_l\delta\boldsymbol\phi}{\delta\boldsymbol\phi} =δϕ0limδϕ(exp(ϕ))Jlδϕ = − ( R ) ∧ J l =-(R)^{\wedge}J_l =(R)Jl通过上面的过程我们得到了旋转矩阵相对于李代数的求导: ∂ R ∂ ϕ = ∂ ( e x p ( ϕ ∧ ) ) ∂ ϕ = − ( R ) ∧ J l \frac {\partial R}{\partial\boldsymbol\phi}=\frac {\partial(exp(\boldsymbol\phi^{\wedge}))}{\partial\boldsymbol\phi}=-(R)^{\wedge}J_l ϕR=ϕ(exp(ϕ))=(R)Jl书中说到 J l J_l Jl的计算很复杂,所以求导时候,并不采用这种方法,而是采用下面介绍的扰动模型的方法。

扰动模型(左乘)

以左乘为例,我们在对 R R R左乘一个微小量 Δ R \Delta R ΔR,就可以得到下一个姿态为 Δ R ∗ R \Delta R*R ΔRR,我们设这左扰动的李代数为 φ \boldsymbol\varphi φ,然后再次使用导数定义对 ∂ R ∂ φ \frac {\partial R}{\partial\boldsymbol\varphi} φR进行求导:
∂ R ∂ ϕ = lim ⁡ φ → 0 e x p ( φ ∧ ) ∗ e x p ( ϕ ∧ ) − e x p ( ϕ ∧ ) φ \frac {\partial R}{\partial\boldsymbol\phi} = \lim_{\boldsymbol\varphi \to 0} \frac {exp(\boldsymbol\varphi^{\wedge})*exp(\boldsymbol\phi^{\wedge}) - exp(\boldsymbol\phi^{\wedge})} {\boldsymbol\varphi} ϕR=φ0limφexp(φ)exp(ϕ)exp(ϕ)
与前面的思路一样,先对 e x p ( φ ∧ ) exp(\boldsymbol\varphi^{\wedge}) exp(φ)进行泰勒展开,然后保留低阶项,最终可以得到如下结论:
∂ R ∂ ϕ = − ( R ) ∧ (11) \frac {\partial R}{\partial\boldsymbol\phi} =-(R)^{\wedge} \tag{11} ϕR=(R)(11)
两种求导的方法,至于哪个精度更高,说实话还得就实际情况才能知道,但是扰动模型,显然计算量上要少非常多。
  
  同样的,变换矩阵的李代数求导,也可以类比获得,直接看书上的结论就可以了!
注意:不管是李代数求导还是扰动模型,都是旋转矩阵对李代数的求导,请你仔细观察一下!

实践

实践部分,请注意一定要使用作者Github上提供的Sophus库,不要使用Sophus官方的库,因为现在Sophus已经是模板类的方法编写的了,书中的例子已经不能直接使用最新版本的Sophus。

题外话:说实话这一讲,有一点儿难,特别是其中的证明特别多,而且概念之间的跳跃也很大,理解上来说是需要时间的,我已经尽量省去了很多不必要的内容,但是还是显得有点乱,你在学习的时候,如果实在不能理解证明过程,请先记住结论,但是在记住结论的同时,你要知道这个公式是用来干啥的。就像我们不知道电脑是怎么生产出来的,但是我们会用就行了。

人生在勤,不索何获 ——张衡

这篇关于解读《视觉SLAM十四讲》,带你一步一步入门视觉SLAM—— 第 4 讲 李群与李代数 (下)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/1033731

相关文章

C++必修:模版的入门到实践

✨✨ 欢迎大家来到贝蒂大讲堂✨✨ 🎈🎈养成好习惯,先赞后看哦~🎈🎈 所属专栏:C++学习 贝蒂的主页:Betty’s blog 1. 泛型编程 首先让我们来思考一个问题,如何实现一个交换函数? void swap(int& x, int& y){int tmp = x;x = y;y = tmp;} 相信大家很快就能写出上面这段代码,但是如果要求这个交换函数支持字符型

零基础STM32单片机编程入门(一)初识STM32单片机

文章目录 一.概要二.单片机型号命名规则三.STM32F103系统架构四.STM32F103C8T6单片机启动流程五.STM32F103C8T6单片机主要外设资源六.编程过程中芯片数据手册的作用1.单片机外设资源情况2.STM32单片机内部框图3.STM32单片机管脚图4.STM32单片机每个管脚可配功能5.单片机功耗数据6.FALSH编程时间,擦写次数7.I/O高低电平电压表格8.外设接口

十四、观察者模式与访问者模式详解

21.观察者模式 21.1.课程目标 1、 掌握观察者模式和访问者模式的应用场景。 2、 掌握观察者模式在具体业务场景中的应用。 3、 了解访问者模式的双分派。 4、 观察者模式和访问者模式的优、缺点。 21.2.内容定位 1、 有 Swing开发经验的人群更容易理解观察者模式。 2、 访问者模式被称为最复杂的设计模式。 21.3.观察者模式 观 察 者 模 式 ( Obser

ps基础入门

1.基础      1.1新建文件      1.2创建指定形状      1.4移动工具          1.41移动画布中的任意元素          1.42移动画布          1.43修改画布大小          1.44修改图像大小      1.5框选工具      1.6矩形工具      1.7图层          1.71图层颜色修改          1

C++入门01

1、.h和.cpp 源文件 (.cpp)源文件是C++程序的实际实现代码文件,其中包含了具体的函数和类的定义、实现以及其他相关的代码。主要特点如下:实现代码: 源文件中包含了函数、类的具体实现代码,用于实现程序的功能。编译单元: 源文件通常是一个编译单元,即单独编译的基本单位。每个源文件都会经过编译器的处理,生成对应的目标文件。包含头文件: 源文件可以通过#include指令引入头文件,以使

LVGL快速入门笔记

目录 一、基础知识 1. 基础对象(lv_obj) 2. 基础对象的大小(size) 3. 基础对象的位置(position) 3.1 直接设置方式 3.2 参照父对象对齐 3.3 获取位置 4. 基础对象的盒子模型(border-box) 5. 基础对象的样式(styles) 5.1 样式的状态和部分 5.1.1 对象可以处于以下状态States的组合: 5.1.2 对象

C语言入门系列:探秘二级指针与多级指针的奇妙世界

文章目录 一,指针的回忆杀1,指针的概念2,指针的声明和赋值3,指针的使用3.1 直接给指针变量赋值3.2 通过*运算符读写指针指向的内存3.2.1 读3.2.2 写 二,二级指针详解1,定义2,示例说明3,二级指针与一级指针、普通变量的关系3.1,与一级指针的关系3.2,与普通变量的关系,示例说明 4,二级指针的常见用途5,二级指针扩展到多级指针 小结 C语言的学习之旅中,二级

打造坚固的SSH防护网:端口敲门入门指南

欢迎来到我的博客,代码的世界里,每一行都是一个故事 🎏:你只管努力,剩下的交给时间 🏠 :小破站 打造坚固的SSH防护网:端口敲门入门指南 前言什么是端口敲门端口敲门的优点1. 增强安全性2. 动态防火墙规则3. 隐匿服务4. 改善日志管理5. 灵活性和兼容性6. 低资源消耗7. 防御暴力破解和扫描8. 便于合法用户访问9. 适用于不同类型的服务 端口敲

好书推荐《深度学习入门 基于Python的理论与实现》

如果你对Python有一定的了解,想对深度学习的基本概念和工作原理有一个透彻的理解,想利用Python编写出简单的深度学习程序,那么这本书绝对是最佳的入门教程,理由如下:     (1)撰写者是一名日本普通的AI工作者,主要记录了他在深度学习中的笔记,这本书站在学习者的角度考虑,秉承“解剖”深度学习的底层技术,不使用任何现有的深度学习框架、尽可能仅使用基本的数学知识和Python库。从零创建一个

手把手教你入门vue+springboot开发(五)--docker部署

文章目录 前言一、前端打包二、后端打包三、docker运行总结 前言 前面我们重点介绍了vue+springboot前后端分离开发的过程,本篇我们结合docker容器来研究一下打包部署过程。 一、前端打包 在VSCode的命令行中输入npm run build可以打包前端代码,出现下图提示表示打包完成。 打包成功后会在前端工程目录生成dist目录,如下图所示: 把