一、关于SURF算法

SURF,我们简单介绍一下,英语全称为SpeededUp Robust Features,直译的话就是“加速版的具有鲁棒性的特征“算法,由Bay在2006年首次提出。SURF是尺度不变特征变换算法(SIFT算法)的加速版。一般来说,标准的SURF算子比SIFT算子快好几倍,并且在多幅图片下具有更好的稳定性。SURF最大的特征在于采用了harr特征以及积分图像的概念,这大大加快了程序的运行时间。SURF可以应用于计算机视觉的物体识别以及3D重构中。

OpenCV中关于SURF算法的部分,常常涉及到的是SURF、SurfFeatureDetector、SurfDescriptorExtractor这三个类;

features2d.hpp头文件中,有:typedef SURF SurfFeatureDetector;和typedef SURF SurfDescriptorExtractor;typedef声明是为现有类型创建一个新的名字,类型别名,即SURF类有了两个新名字SurfFeatureDetector以及SurfDescriptorExtractor。

也就是说,SurfFeatureDetector类和SurfDescriptorExtractor类,其实就是SURF类,他们三者等价。

由类的继承,追根溯源可得:

<span style="font-size:14px;"><span style="font-size:14px;">int minHessian = 400;      设定阈值minHessian,关系到最后提取的特征点,这个是surf算法的一个参数;
SurfFeatureDetector detector( minHessian );
std::vector< KeyPoint > keypoints_object, keypoints_scene;  定义两个KeyPoint 向量keypoints_object, keypoints_scene来存放检测出来的特征点;
detector.detect( gray_image1, keypoints_object );
detector.detect( gray_image2, keypoints_scene );
</span></span>
<span style="font-size:14px;"><span style="font-size:14px;">SurfDescriptorExtractor extractor;声明的surf类提取器;
Mat descriptors_1, descriptors_2;定义两个Mat类矩阵:descriptors_1, descriptors_2,存放提取出来的关键点;
extractor.compute( img_1, keypoints_1, descriptors_1 );
extractor.compute( img_2, keypoints_2, descriptors_2 );</span></span>

二、drawKeypoints()

作用:绘制关键点。

形式:void drawKeypoints(const Mat&image, const vector<KeyPoint>& keypoints, Mat& outImage, constScalar& color=Scalar::all(-1), int flags=DrawMatchesFlags::DEFAULT );

参数:

image:const Mat&类型的src,输入图像;
keypoints:const vector<KeyPoint>&类型的keypoints,根据源图像得到的特征点,它是一个输出参数;
outImage:Mat&类型的outImage,输出图像,其内容取决于第五个参数标识符falgs;
color:const Scalar&类型的color,关键点的颜色,有默认值Scalar::all(-1);
flags:int类型的flags,绘制关键点是的特征标识符,有默认值DrawMatchesFlags::DEFAULT;

三、用BruteForceMatcher类中的函数match来匹配两幅图像的特征向量

相关代码如下:

<span style="font-size:14px;"><span style="font-size:14px;"><span style="font-size:14px;">//实例化一个匹配器BruteForceMatcher<L2<float> > matcher;std::vector<DMatch > matches;//匹配两幅图中的描述子(descriptors)matcher.match(descriptors1, descriptors2, matches );</span></span></span>

BruteForceMatcher是由DescriptorMatcher派生出来的一个类,而DescriptorMatcher定义了不同的匹配策略的共同接口。调用match方法后,在其第三个参数输出一个cv::DMatch向量。于是我们定义一个std::vector<DMatch>类型的matches。

四、drawMatches()

作用:从两幅图片中画出发现的匹配的关键点。

形式:void drawMatches(const Mat& img1, const vector<KeyPoint>& keypoints1, const Mat& img2, const vector<KeyPoint>& keypoints2, const vector<DMatch>& matches1to2, Mat& outImg, const Scalar& matchColor=Scalar::all(-1), const Scalar& singlePointColor=Scalar::all(-1), const vector<char>& matchesMask=vector<char>(), int flags=DrawMatchesFlags::DEFAULT );

参数:

img1、img2:两幅源图像;
keypoints1、keypoints2:两幅源图像中的关键点;

matches1to2:从第一幅图像来匹配第二幅图像,即从keypoints1[i]中寻找与keypoints2[i]的对应点;

outImg:输出图像;它的值取决于flags--在图像中绘制的内容;

matchColor:匹配颜色(线和点的颜色),如果matchColor==Scalar::all(-1),颜色随机生成;

singlePointColor:单个关键点的颜色,即没有关键点与之匹配,如果matchColor==Scalar::all(-1),颜色随机生成;

matchesMask:掩码决定画哪个匹配的关键点,如果掩码为空,画出所有的匹配的关键点;

flags:设置绘图功能,可能标志位的值由“DrawMatchesFlags”确定;

五、FlannBasedMatcher

算法更快但是找到的是最近邻近似匹配,所以当我们需要找到一个相对好的匹配但是不需要最佳匹配的时候往往使用FlannBasedMatcher。当然也可以通过调整FlannBasedMatcher的参数来提高匹配的精度或者提高算法速度,但是相应地算法速度或者算法精度会受到影响。

<span style="font-size:14px;"><span style="font-size:14px;">  FlannBasedMatcher matcher;std::vector< DMatch > matches;       定义了一个DMatch类向量matches,用来存放descriptors_1, descriptors_2中匹配的关键点matcher.match( descriptors_1, descriptors_2, matches );
</span></span>

六、push_back()

算法语言里面的一个函数名,如c++中的vector头文件里面就有这个push_back函数,在vector类中作用为在vector尾部加入一个数据,如:good_matches.push_back( matches[i]);把matches[i]加到向量good_matches的最后一位。

七、findHomography()

作用:寻找两个平面匹配上的关键点的变换。

形式:Mat findHomography(InputArray srcPoints, InputArray dstPoints, int method=0, double ransacReprojThreshold=3, OutputArray mask=noArray() );

参数:

srcPoints:原始平面中点的坐标,即一个CV_32FC2 or vector<Point2f> 型矩阵;

dstPoints:目标平面中点的坐标,即一个CV_32FC2 or vector<Point2f> 型矩阵;

method:用于计算单应矩阵的方法--0:使用所有点的常规方法;

CV_RANSAC:基于RANSAC的鲁棒方法;

CV_LMEDS:最不平均方法;

ransacReprojThreshold:仅当使用CV_RANSAC方法时,把一双点作为内窗的最大投影误差;

mask:鲁棒方法的可选输出掩码设置;

八、perspectiveTransform()

作用:向量的投影矩阵转换;

形式:void perspectiveTransform(InputArray src, OutputArray dst, InputArray m);

参数:

src:输入2通道或3通道的浮点阵列,每个元素是一个将被转换的2D/3D向量;

dst:与输入有相同大小和类型的输出矩阵;

m:3x3 或4x4的浮点转换矩阵;

<span style="font-size:14px;"><span style="font-size:14px;"><span style="font-size:14px;"><span style="font-size:14px;">#include <stdio.h>
#include <iostream>
#include "opencv2/core/core.hpp"
#include "opencv2/features2d/features2d.hpp"
#include "opencv2/highgui/highgui.hpp"
#include "opencv2/nonfree/nonfree.hpp"
using namespace cv;void readme();/** @function main */
int main( int argc, char** argv )
{if( argc != 1 ){ readme(); return -1; }Mat img_1 = imread("8.jpg", CV_LOAD_IMAGE_GRAYSCALE );Mat img_2 = imread("9.jpg", CV_LOAD_IMAGE_GRAYSCALE );if( !img_1.data || !img_2.data ){ std::cout<< " --(!) Error reading images " << std::endl; return -1; }//-- Step 1: Detect the keypoints using SURF Detectorint minHessian = 400;SurfFeatureDetector detector( minHessian );std::vector<KeyPoint> keypoints_1, keypoints_2;detector.detect( img_1, keypoints_1 );detector.detect( img_2, keypoints_2 );//-- Draw keypointsMat img_keypoints_1; Mat img_keypoints_2;drawKeypoints( img_1, keypoints_1, img_keypoints_1, Scalar::all(-1), DrawMatchesFlags::DEFAULT );drawKeypoints( img_2, keypoints_2, img_keypoints_2, Scalar::all(-1), DrawMatchesFlags::DEFAULT );//-- Show detected (drawn) keypointsimshow("Keypoints 1", img_keypoints_1 );imshow("Keypoints 2", img_keypoints_2 );waitKey(0);return 0;}/** @function readme */void readme(){ std::cout << " Usage: ./SURF_detector <img1> <img2>" << std::endl; }</span></span></span></span>
<span style="font-size:14px;"><span style="font-size:14px;">#include <stdio.h>
#include <iostream>
#include "opencv2/core/core.hpp"
#include "opencv2/features2d/features2d.hpp"
#include "opencv2/highgui/highgui.hpp"using namespace cv;void readme();/** @function main */
int main( int argc, char** argv )
{if( argc != 3 ){ return -1; }Mat img_1 = imread( argv[1], CV_LOAD_IMAGE_GRAYSCALE );Mat img_2 = imread( argv[2], CV_LOAD_IMAGE_GRAYSCALE );if( !img_1.data || !img_2.data ){ return -1; }//-- Step 1: Detect the keypoints using SURF Detectorint minHessian = 400;SurfFeatureDetector detector( minHessian );std::vector<KeyPoint> keypoints_1, keypoints_2;detector.detect( img_1, keypoints_1 );detector.detect( img_2, keypoints_2 );//-- Step 2: Calculate descriptors (feature vectors)SurfDescriptorExtractor extractor;Mat descriptors_1, descriptors_2;extractor.compute( img_1, keypoints_1, descriptors_1 );extractor.compute( img_2, keypoints_2, descriptors_2 );//-- Step 3: Matching descriptor vectors with a brute force matcherBruteForceMatcher< L2<float> > matcher;std::vector< DMatch > matches;matcher.match( descriptors_1, descriptors_2, matches );//-- Draw matchesMat img_matches;drawMatches( img_1, keypoints_1, img_2, keypoints_2, matches, img_matches );//-- Show detected matchesimshow("Matches", img_matches );waitKey(0);return 0;}/** @function readme */void readme(){ std::cout << " Usage: ./SURF_descriptor <img1> <img2>" << std::endl; }</span></span>

SURF特征点检测--SurfFeatureDetector、SurfDescriptorExtractor和FlannBasedMatcher相关推荐

  1. 【OpenCV入门教程之十七】OpenCV重映射 SURF特征点检测合辑

    本系列文章由@浅墨_毛星云 出品,转载请注明出处. 文章链接: http://blog.csdn.net/poem_qianmo/article/details/30974513 作者:毛星云(浅墨) ...

  2. opencv——SURF特征点检测并使用Flann算法匹配

    记录一下学习过程,话不多说贴代码: #include <opencv2/core/core.hpp> #include <opencv2/features2d/features2d. ...

  3. SURF 特征点检测

    SURF可以用于对象定位和识别.人脸识别.3D重建.对象跟踪和提取兴趣点等.常用来进行物体辨识和图像匹配. 1.SURF 全称 speed up robust feature 是加速版的SIFT 2. ...

  4. Android OpenCV(五十八):SURF特征点检测

    SURF 特征点 SUFR (Speed Up Robust Fetures) ,是对 SIFT 算法的一种改进.SIFT (Scale-invariant Feature Transform) 即尺 ...

  5. opencv surf特征点检测(二),API接口分析

    本章内容: * 1. 单张图像的特征点计算  cv::xfeatures2d::SURF->detect          * 2. 图像集合的特征点计算 cv::xfeatures2d::SU ...

  6. SURF算法与SIFT算法的性能比较——图像特征点检测与提取算法分析

    图像特征点提取算法的算法研究(SURF和SIFT算法) 1. 摘要 计算机视觉中,很大一部分研究集中在图像特征提取和特征生成算法上.对图像的优化,不同于一般数学问题的优化方法,图像的优化是对像素点,在 ...

  7. 特征点检测学习_2(surf算法)

    特征点检测学习_2(surf算法) 在上篇博客特征点检测学习_1(sift算法) 中简单介绍了经典的sift算法,sift算法比较稳定,检测到的特征点也比较多,其最大的确定是计算复杂度较高.后面有不少 ...

  8. surf程序 matlab,Matlab图像处理学习笔记(七):surf特征点

    本文主要演示如何使用matlab自带的Computer Vision System Toolbox这个工具箱进行suft特征点的检测.匹配及显示.这个工具箱是matlab2012b及之后才有的一个工具 ...

  9. OpenCV特征点检测------Surf(特征点篇)

    Surf(Speed Up Robust Feature) Surf算法的原理                                                              ...

最新文章

  1. mysql 优化详解_MySQL 优化详解
  2. Linux C编程之一:Linux下c语言的开发环境
  3. Scikit Learn: 在python中机器学习
  4. 获取微软产品下载链接
  5. Charles弱网测试(Web)
  6. 程序猿们,别着急入手区块链,先给自己选好武林门派再练功不迟
  7. cmake卸载 ubuntu_ubuntu卸载/更新Cmake
  8. uva-10887-枚举
  9. xml2 交叉编译移植
  10. 菜鸟学asp.net遇到的问题和解决方案
  11. 使用DirectShow.NET获取摄像头视频流
  12. PC端 二维码/条形码扫描器1.1-支持截图+摄像头+本地图片+扫描枪识别
  13. python调用hive与java调用区别_使用Pyhive调用
  14. OpenAI Whisper论文笔记
  15. 2021-07-27 Vue修改主页
  16. VR全景有什么应用,和传统摄影的区别,发展前景如何?
  17. Open3d读写ply点云文件
  18. perl linux 遍历文件,Perl/Linux过滤大文件与其他文件的内容
  19. 免费视频教程:嵌入式stm32项目开发之心率检测仪的设计与实现
  20. 谈谈那些年玩RPG游戏时的疯狂举动

热门文章

  1. python好玩的教程_用python真的可以做很多有趣的事!我自己做了些小项目!大家看看...
  2. 2021年茶艺师(初级)考试报名及茶艺师(初级)找解析
  3. 我是如何被逼出软件行业的(一)
  4. Codevs3324 新斯诺克
  5. shell读书笔记9
  6. 判定IP地址合法性的三种方法
  7. 哈工大数理逻辑之ND系统总结和例题题解
  8. HTML页面唤醒微信
  9. App Annie报告:电邮将被移动时代下的年轻人抛弃
  10. FileZilla Server源码解析之LIST命令