双目立体匹配算法漫谈
双目立体匹配算法是计算机视觉中比较经典的问题。有大量经典的双目立体匹配算法。本文简要介绍一下双目立体匹配的常用基本流程,也可以说是套路。 第一次写这么长的博文,我想到哪里写哪里。
更详细内容的可见文章A Taxonomy and Evaluation of Dense Two-Frame Stereo Correspondence Algorithms。
测试数据:www.middlebury.edu/stereo
前提
通常来说,硬件采集的图像首先经过畸变矫正,极线纠正,然后进行立体匹配,最后三角化为点云。如图1所示。首先需要说明的是,这里讲的立体匹配算法假定图像已经经过极线1纠正,从而两幅图像极线约束匹配变成图像的一行内匹配问题。在图1中对应的为红色的部分。以下没有特殊说明,两幅图像均指经过极线纠正后的图像。立体匹配问题这里主要考虑怎样计算极线纠正后的两幅图像之间的视差图。因为在基线和焦距已知的情况下,视差图可以和深度图互相转换,从而完成由双目估计物体深度(三维信息)的工作。
一些基本假设
如果物体是一个朗伯体2,或者说物体表面是朗伯表面,那么,从任意位置和方向看物体表面同一点,得到的辐射能量是相同的。在可见光范围内,辐射也可以简单理解为RGB颜色值。那么匹配问题自然是按行寻找相同颜色的像素。理想很丰满,现实很骨感。一方面有可能在图像同一行内出现相同的颜色,无法区分。另一方面现实世界物体很难是一个朗伯体,即便是表面同一个点,在不同图像上的颜色都有差异。所以就有了诸多的算法来解决这些问题。
首先可以假设物体表面深度是连续的,或者是分段连续的。(因为前文说了视差和深度在基线和焦距已知的情况可以相互转换,这里有时候说视差,有时候说深度,不必在意)。这样在图像邻域之间可以产生一个平滑约束。另外虽然场景不是一个朗伯表面,但是不同相机看相同点颜色还是非常接近的。
框架
现在讲一讲立体匹配的套路。主要由四个算法模块组成:
- matching cost computation; 匹配代价的计算
- cost (support) aggregation;代价聚合
- disparity computation/optimization; 视差图计算
- disparity refinement;视差图优化
matching cost computation
一个简单的想法是对于灰度图像,直接计算像素之间灰度差来作为匹配代价。但是这不够鲁棒。通常采用一个以当前像素为中心的window来代替像素,这些像素可以排成一个向量。向量的值为像素的灰度值。这样两个像素的匹配问题就转换成两个向量之间的距离。可以是L1,L2,或者夹角的余弦值等等。可以参考MAD、SAD、SSD、MSD、NCC、SSDA、SATD等匹配算子。
cost (support) aggregation;代价聚合
代价聚合通常是一个立体匹配算法中非常关键的部分。因为一些噪声,光照差异,颜色不同和匹配歧义,匹配代价最优(代价最小)的不一定是真正的同名点,可以通过假设场景是连续的来进行处理。比较容易想到的是要考虑每个像素邻域信息。这里如果考虑某个像素与周围所有图像的关系,那么就是一个全局算法:如果仅仅考虑局部窗口内,那么就是一个局部算法。还有一种介于二者之间,称为半全局算法。显然,考虑的越多,计算量越大,但效果越好。通常来说,全局算法较慢,到效果很棒。