上一篇介绍了双目立体匹配SAD算法,这一篇介绍Census算法。
Census原理:
在视图中选取任一点,以该点为中心划出一个例如3 × 3 的矩形,矩形中除中心点之外的每一点都与中心点进行比较,灰度值小于中心点记为1,灰度大于中心点的则记为0,以所得长度为 8 的只有 0 和 1 的序列作为该中心点的 census 序列,即中心像素的灰度值被census 序列替换。经过census变换后的图像使用汉明距离计算相似度,所谓图像匹配就是在匹配图像中找出与参考像素点相似度最高的点,而汉明距正是匹配图像像素与参考像素相似度的度量。具体而言,对于欲求取视差的左右视图,要比较两个视图中两点的相似度,可将此两点的census值逐位进行异或运算,然后计算结果为1 的个数,记为此两点之间的汉明值,汉明值是两点间相似度的一种体现,汉明值愈小,两点相似度愈大实现算法时先异或再统计1的个数即可,汉明距越小即相似度越高。

下面的代码是自己根据原理写的,实现的结果并没有很好,以后继续优化代码。

具体代码如下:

//*************************Census*********************
#include <iostream>
#include <opencv2/opencv.hpp>
#include <opencv2/imgproc.hpp>
#include <opencv2/highgui.hpp>using namespace std;
using namespace cv;//-------------------定义汉明距离----------------------------
int disparity;
int GetHammingWeight(uchar value);//求1的个数//-------------------定义Census处理图像函数---------------------
int hWind = 1;//定义窗口大小为(2*hWind+1)
Mat ProcessImg(Mat &Img);//将矩形内的像素与中心像素相比较,将结果存于中心像素中
Mat Img_census, Left_census, Right_census;//--------------------得到Disparity图像------------------------
Mat getDisparity(Mat &left, Mat &right);//--------------------处理Disparity图像-----------------------
Mat ProcessDisparity(Mat &disImg);int ImgHeight, ImgWidth;//int num = 0;//异或得到的海明距离
Mat LeftImg, RightImg;
Mat DisparityImg(ImgHeight, ImgWidth, CV_8UC1, Scalar::all(0));
Mat DisparityImg_Processed(ImgHeight, ImgWidth, CV_8UC1, Scalar::all(0));
Mat DisparityImg_Processed_2(ImgHeight, ImgWidth, CV_8UC1);
//定义读取图片的路径
string file_dir="C:\\Program Files\\FLIR Integrated Imaging Solutions\\Triclops Stereo Vision SDK\\stereomatching\\Grab_Stereo\\pictures\\";
//定义存储图片的路径
string save_dir= "C:\\Program Files\\FLIR Integrated Imaging Solutions\\Triclops Stereo Vision SDK\\stereomatching\\Grab_Stereo\\Census\\";int main()
{LeftImg = imread(file_dir + "renwu_left.png", 0);RightImg = imread(file_dir + "renwu_right.png", 0);namedWindow("renwu_left", 1);namedWindow("renwu_right", 1);imshow("renwu_left", LeftImg);waitKey(5);imshow("renwu_right", RightImg);waitKey(5);ImgHeight = LeftImg.rows;ImgWidth = LeftImg.cols;Left_census= ProcessImg(LeftImg);//处理左图,得到左图的CENSUS图像 Left_censusnamedWindow("Left_census", 1);imshow("Left_census", Left_census);waitKey(5);
//  imwrite(save_dir + "renwu_left.jpg", Left_census);Right_census= ProcessImg(RightImg);namedWindow("Right_census", 1);imshow("Right_census", Right_census);waitKey(5);
//  imwrite(save_dir  + "renwu_right.jpg", Right_census);DisparityImg= getDisparity(Left_census, Right_census);namedWindow("Disparity", 1);imshow("Disparity", DisparityImg);
//  imwrite(save_dir  + "disparity.jpg", DisparityImg);waitKey(5);DisparityImg_Processed = ProcessDisparity(DisparityImg);namedWindow("DisparityImg_Processed", 1);imshow("DisparityImg_Processed", DisparityImg_Processed);
//  imwrite(save_dir + "disparity_processed.jpg", DisparityImg_Processed);waitKey(0);return 0;
}//-----------------------对图像进行census编码---------------
Mat ProcessImg(Mat &Img)
{int64 start, end;start = getTickCount();Mat Img_census = Mat(Img.rows, Img.cols, CV_8UC1, Scalar::all(0));uchar center = 0;for (int i = 0; i < ImgHeight - hWind; i++){for (int j = 0; j < ImgWidth - hWind; j++){center = Img.at<uchar>(i + hWind, j + hWind);uchar census = 0;uchar neighbor = 0;for (int p = i; p <= i + 2 * hWind; p++)//行{for (int q = j; q <= j + 2 * hWind; q++)//列{if (p >= 0 && p <ImgHeight  && q >= 0 && q < ImgWidth){if (!(p == i + hWind && q == j + hWind)){//--------- 将二进制数存在变量中-----neighbor = Img.at<uchar>(p, q);if (neighbor > center){census = census * 2;//向左移一位,相当于在二进制后面增添0}else{census = census * 2 + 1;//向左移一位并加一,相当于在二进制后面增添1}//cout << "census = " << static_cast<int>(census) << endl;}}}}Img_census.at<uchar>(i + hWind, j + hWind) = census;}}/*end = getTickCount();cout << "time is = " << end - start << " ms" << endl;*/return Img_census;
}//------------得到汉明距离---------------
int GetHammingWeight( uchar value)
{int num = 0;if (value == 0)return 0;while (value){++num;value = (value - 1)&value;}return num;
}//--------------------得到视差图像--------------
Mat getDisparity(Mat &left, Mat &right)
{int DSR =16;//视差搜索范围Mat disparity(ImgHeight,ImgWidth,CV_8UC1);cout << "ImgHeight = " << ImgHeight << "   " << "ImgWidth = " << ImgWidth << endl;for (int i = 0; i < ImgHeight; i++){for (int j = 0; j < ImgWidth; j++){uchar L;uchar R;uchar diff;L = left.at<uchar>(i, j);Mat Dif(1, DSR, CV_8UC1);
//          Mat Dif(1, DSR, CV_32F);for (int k = 0; k < DSR; k++){//cout << "k = " << k << endl;int y = j - k;if (y < 0){Dif.at<uchar>(k) = 0;}if (y >= 0){R = right.at<uchar>(i,y);//bitwise_xor(L, R, );diff = L^R;diff = GetHammingWeight(diff);Dif.at<uchar>(k) = diff;
//                  Dif.at<float>(k) = diff;}}//---------------寻找最佳匹配点--------------Point minLoc;minMaxLoc(Dif, NULL, NULL, &minLoc, NULL);int loc = minLoc.x;//cout << "loc..... = " << loc << endl;disparity.at<uchar>(i,j)=loc*16;}}return disparity;
}//-------------对得到的视差图进行处理-------------------
Mat ProcessDisparity(Mat &disImg)
{Mat ProcessDisImg(ImgHeight,ImgWidth,CV_8UC1);//存储处理后视差图for (int i = 0; i < ImgHeight; i++){for (int j = 0; j < ImgWidth; j++){uchar pixel = disImg.at<uchar>(i, j);if (pixel < 100)pixel = 0;ProcessDisImg.at<uchar>(i, j) = pixel;}}return ProcessDisImg;
}


经过处理后的左图census图像


经过处理后的右图census图像


disparity图像


处理后的disparity图像

实现结果并没有那么好,希望有经验的读者可以留言提供更好的建议。谢谢。

双目立体匹配 Census相关推荐

  1. 双目立体匹配经典算法之Semi-Global Matching(SGM)概述:匹配代价计算之互信息(Mutual Information,MI)...

      半全局立体匹配算法Semi-Global Matching,SGM由学者Hirschmüller在2005年所提出1,提出的背景是一方面高效率的局部算法由于所基于的局部窗口视差相同的假设在很多情况 ...

  2. 双目立体匹配步骤详解

    点击上方"3D视觉工坊",选择"星标" 干货第一时间送达 来源:https://blog.csdn.net/rs_lys/article/details/833 ...

  3. 双目立体匹配入门【一】(理论)

    文章目录 参考文章 1 专有名词 2 双目视觉基础 1 针孔摄像机模型 2 双目交会 3 立体测量的基本原理:三角化 4 极线约束 5 极线校正/立体校正 6 立体匹配难点 7 立体匹配方法分类 8 ...

  4. 双目立体匹配之匹配代价计算

    文章目录 AD SAD Cencus AD-Cencus 之前谈到过双目立体匹配的步骤,主要分为四步(半全局方法):匹配代价计算.代价聚合.视差计算.视差优化.匹配代价计算是双目立体匹配的第一步,其有 ...

  5. 双目立体匹配 等 算法 论文 综述 全局局部算法 CSCA NLCA SegmentTree树 DoubleBP Belief-Propagation AD-Census SGM

    双目立体匹配 等 算法 论文 综述 本文GITHUB 博文末尾支持二维码赞赏哦 _ 双目立体视觉技术实质就是模拟人的双眼视觉处理系统来处理通过摄像机采集所 获取的图像,它利用两台或多台摄像机在一定约束 ...

  6. python 立体匹配_双目立体匹配步骤详解

    点击上方"小白学视觉",选择加"星标"或"置顶" 重磅干货,第一时间送达 来源: https://blog.csdn.net/rs_lys/ ...

  7. 双目立体匹配——归一化互相关(NCC)

    归一化相关性,normalization cross-correlation,因此简称NCC,下文中笔者将用NCC来代替这冗长的名称. NCC,顾名思义,就是用于归一化待匹配目标之间的相关程度,注意这 ...

  8. 真实场景的双目立体匹配(Stereo Matching)获取深度图详解

    点击上方"小白学视觉",选择加"星标"或"置顶" 重磅干货,第一时间送达 双目立体匹配一直是双目视觉的研究热点,双目相机拍摄同一场景的左.右 ...

  9. 双目立体匹配修炼之路

    文章目录 前言 一.双目立体匹配是什么? 1.双目视觉: 2. 视差: 3."对极约束"概念: 4. 对极几何(Epipolar Geometry) 5. 如何计算得到深度呢? 二 ...

最新文章

  1. visual studio 自动整理代码
  2. tensorrt yolov5 批量预测学习笔记
  3. 如何在两个目录中删除其中一个目录中同名文件
  4. Java 多线程(四)—— 单例模式
  5. 卧槽!12个杭州阿里高学历女员工被初中男骗财骗色1900多万!骗子冒充有钱佬!开豪车保时捷勾搭妹子,法院判无期徒刑!...
  6. POJ 1804 Brainman (归并排序 -- 求逆序对数)
  7. 泛型数组 c# 0104
  8. 类与类关系的UML图与代码表现
  9. golang之网络开发
  10. Android模拟器体验有感
  11. menu什么意思中文意思_pipeline什么意思
  12. php mvc 路由,PHP MVC框架路由学习笔记
  13. 12,mac phpstorm xdebug
  14. Trie字典树数组实现
  15. Qt+VS2015+番茄助手 个人常用快捷键集锦
  16. SeaweedFS介绍安装集群部署总结
  17. 一元四次方程的求根公式
  18. 第一次安装使用rsync服务进行两台服务器之间的文件同步,并排查客户端到服务端网络不通的问题。
  19. 荣耀十支持鸿蒙OS,不是所有华为荣耀手机都能升级华为鸿蒙OS,只有这48款才行...
  20. webservice 菜鸟探索之旅

热门文章

  1. 智能优化算法:战争策略算法-附代码
  2. 传播智客黑马Java学习笔记_day06
  3. VxWorks6.6移植嵌入式ICE中间件解决方案
  4. MyBatis No MyBatis mapper was found in ‘[xx.mapper]‘ package. Please check your configuration
  5. 气象数据随时随地:让天气预报API为您的应用提供精准的天气信息
  6. 从数据库中查询日历SQL
  7. 传统IT架构云化会给运维带来哪些变化?
  8. 学习数学思维推荐阅读的五本数学书籍
  9. 离散化(保序 / 非保序)
  10. 红色梦幻背景爱情flash动画