天天看点

建图 | SVO 论文与代码分析分讲

建图(深度滤波器)

建图 | SVO 论文与代码分析分讲

VO 把像素的深度误差模型看做概率分布,使用 高斯——均匀混合分布的逆深度(深度值服从高斯分布,局外点的概率服从 Beta 分布),称为 深度滤波器 Depth Filter,每个特征点作为 种子 Seed(深度未收敛的像素点)有一个单独的深度滤波器。

  • 初始化种子:如果进来一个 关键帧,就提取关键帧上的新特征点,初始化深度滤波器,作为种子点放进一个种子队列中
  • 更新种子:如果进来一个 普通帧,就用普通帧的信息,更新所有种子点的概率分布;如果某个种子点的深度分布已经收敛,就把它放到地图中,供追踪线程使用

初始化种子

代码主要在 DepthFilter::initializeSeeds。

  • 当前帧上已经有的特征点,占据住网格
  • 多层金字塔 FAST 特征检测并进行非极大值抑制,映射到第 0 层网格,每个网格保留 Shi-Tomas 分数最大的点
  • 对于所有的新的特征点,初始化成种子点 Seed
  • 高斯分布均值:mu = 1.0/depth_mean
  • 高斯分布方差:sigma2 = z_range*z_range/36,其中 z_range = 1.0/depth_min

更新种子(深度滤波)

深度滤波 DepthFilter::updateSeeds 主要过程:

  • 极线搜索与三角测量 Matcher::findEpipolarMatchDirect
  • 计算深度不确定度 DepthFilter::computeTau
  • 深度融合,更新种子 DepthFilter::updateSeed
  • 初始化新的地图点,移除种子点

深度估计值(极线搜索)

  • 根据 深度均值mu和深度方差sigma2确定深度范围 ,计算极线
  • 计算仿射矩阵 warp::getWarpMatrixAffine(帧间图像发生旋转)
  • 极线上搜索匹配:通过RANSAC计算ZMSSD获取最佳匹配点坐标
  • 当计算的极线长度小于两个像素时,直接采用下一步的图像对齐
  • 否则,继续沿极线搜索匹配
  • 光流法亚像素精度提取(图像对齐) feature_alignment::align2D
  • 三角法恢复深度Z depthFromTriangulation (Triangulate in SVO)

深度估计不确定度

REMODE 对由于特征定位不准导致的三角化深度误差进行了分析

建图 | SVO 论文与代码分析分讲

假设 焦距为

建图 | SVO 论文与代码分析分讲

,像素扰动为px_noise = 1.0,角度变化量px_error_angle为

建图 | SVO 论文与代码分析分讲

建图 | SVO 论文与代码分析分讲

建图 | SVO 论文与代码分析分讲

建图 | SVO 论文与代码分析分讲
建图 | SVO 论文与代码分析分讲

已知

建图 | SVO 论文与代码分析分讲

为 T_ref_cur.translation(),根据正弦定理

建图 | SVO 论文与代码分析分讲

所以,深度不确定度tau为

建图 | SVO 论文与代码分析分讲

逆深度不确定度 tau_inverse 为:

double tau_inverse = 0.5 * (1.0/max(0.0000001, z-tau) - 1.0/(z+tau));

即逆深度标准差为

建图 | SVO 论文与代码分析分讲

深度融合

代码主要在 void DepthFilter::updateSeed(const float x, const float tau2, Seed* seed)。

SVO 的融合是不断利用最新时刻深度的观测值,来融合上一时刻深度最优值,直至深度收敛。

通过上面两步得到逆深度测量值

建图 | SVO 论文与代码分析分讲

1./z 和 逆深度不确定度

建图 | SVO 论文与代码分析分讲

,则 逆深度 服从高斯分布

建图 | SVO 论文与代码分析分讲

SVO 采用 Vogiatzis的论文 Video-based, real-time multi-view stereo 提到的概率模型,使用 高斯–均匀混合分布的深度滤波器,根据

建图 | SVO 论文与代码分析分讲

建图 | SVO 论文与代码分析分讲

更新以下四个参数:

逆深度高斯分布的均值

建图 | SVO 论文与代码分析分讲

seed->mu

逆深度高斯分布的方差

建图 | SVO 论文与代码分析分讲

seed->sigma2

Beta 分布的

建图 | SVO 论文与代码分析分讲

seed->a

Beta 分布的

建图 | SVO 论文与代码分析分讲

seed->b

更新过程(Vogiatzis的Supplementary matterial)如下:

建图 | SVO 论文与代码分析分讲

其中,论文公式 19 有误(代码正确),应为

建图 | SVO 论文与代码分析分讲

最终,得到收敛的逆深度的最佳估计值 seed->mu。

新的地图点

如果种子点的方差seed->sigma2,小于深度范围 /200 的时候,就认为收敛了,它就不再是种子点,而是TYPE_CANDIDATE点。

TYPE_CANDIDATE点被成功观察到 1 次,就变成TYPE_UNKNOWN点;TYPE_UNKNOWN被成功观察到 10 次,就变成TYPE_GOOD点;如果多次应该观察而没有被观察到,就变成TYPE_DELETED点。

总结与讨论:

  • 特征点提取在地图线程,跟踪使用光流法
  • 后端的特征点只在关键帧上提取,用 FAST 加金字塔
  • 上一个关键帧的特征点在这一个关键帧上找匹配点的方法,是用极线搜索,寻找亮度差最小的点,最后再用深度滤波器把这个地图点准确地滤出来
  • 重定位比较简单,没有回环
  • 深度滤波器使用的是高斯–均匀混合分布
  • SVO 对 PTAM 的改进主要在两个方面:高效的特征匹配、鲁棒的深度滤波器
  • 在 Tracking 线程,当前帧的特征点是从上一帧用光流法传递过来的,只有在 Mapping 线程DepthFilter插入新关键帧时才需要提取特征点,不需要每一帧都提取特征点
  • 在 Tracking 线程,当前帧的特征点是从上一帧用光流法传递过来的,只有在 Mapping线程变了(除非BA阶段调整);而 SVO 的深度滤波器会根据多帧图片不断收敛地图点的不确定度,从而得到更可靠的地图点。因为地图点更可靠,所以 SVO 只需要维护更少的地图点(PTAM一般维护约 160 到 220 个特征点,SVO 在 fast 模式下维护约 120 个地图点),从而加快了计算速度。

参考文献:

  • SVO: Fast Semi-Direct Monocular Visual Odometry
  • ivcj2010supp, Supplementary matterial
  • REMODE: Probabilistic, Monocular Dense Reconstruction in Real Time
  • SVO 代码笔记
  • svo: semi-direct visual odometry 论文解析
  • 能否具体解释下svo的运动估计与深度估计两方面?
  • SVO原理解析
  • svo的Supplementary matterial 推导过程
  • 深度滤波器详细解读

继续阅读