版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/xxzxxzdlut/article/details/72930209
特征匹配的结果会得到两个特征集合的对应关系列表。第一组特征集被称为训练集,第二组被称为查询集。FLANN在调用匹配函数之前,为了提高匹配速度,训练一个匹配器。训练阶段是为了优化cv::FlannBasedMatcher的性能。train类将会建立特征集的索引树。
而对于暴力匹配,train类不需要做什么,因为没有预处理。
FLANN和SURF搭配匹配特征点
knnMatch()找每个特征的K近邻匹配
效率不够高,帧率很低。参考《opencv3编程入门》
#include<opencv2/opencv.hpp>
#include<opencv2/features2d/features2d.hpp>
#include<opencv2/xfeatures2d/nonfree.hpp>
#include<opencv2/highgui/highgui.hpp>
#include<iostream>
using namespace std;
using namespace cv;
using namespace cv::xfeatures2d;
int main()
{
Mat trainImage = imread("3.jpg",1);
Mat trainImage_gray;
imshow("原始图",trainImage);
cvtColor(trainImage,trainImage_gray,CV_BGR2GRAY);
vector<KeyPoint>train_keypoint;
Mat trainDescriptor;
Ptr<SurfFeatureDetector> Detector = SurfFeatureDetector::create(80);
Detector->detectAndCompute(trainImage_gray,Mat(),train_keypoint,trainDescriptor);
vector<Mat> train_desc_collection(1,trainDescriptor);
FlannBasedMatcher matcher;
matcher.add(train_desc_collection);
matcher.train();
VideoCapture cap(0);
unsigned int frameCount = 0;
while (char(waitKey(1) != 'q'))
{
int64 time0 = getTickCount();
Mat testImage, testImage_gray;
cap >> testImage;
if (testImage.empty())
continue;
cvtColor(testImage,testImage_gray,CV_BGR2GRAY);
vector<KeyPoint>test_keypoint;
Mat testDescriptor;
Detector->detectAndCompute(testImage_gray,Mat(),test_keypoint,testDescriptor);
vector<vector<DMatch>>matches;
matcher.knnMatch(testDescriptor,matches,2);
vector<DMatch>goodMatches;
for (unsigned int i = 0; i < matches.size(); i++)
{
if (matches[i][0].distance < 0.6*matches[i][1].distance)
goodMatches.push_back(matches[i][0]);
}
Mat dstImage;
drawMatches(testImage,test_keypoint,trainImage,train_keypoint,goodMatches,dstImage);
imshow("匹配窗口",dstImage);
cout << "当前帧率为" << getTickFrequency() / (getTickCount() - time0) << endl;
}
return 0;
}