harris角点检测+sift特征提取匹配组合

#include <iostream>  
#include<opencv2\highgui.hpp>
#include<opencv2\xfeatures2d\nonfree.hpp>
#include<opencv2\opencv.hpp>
#include<opencv2\xfeatures2d.hpp>

using namespace cv;
using namespace std;
using namespace cv::xfeatures2d;

//角点匹配
void harrismatch(Mat img1, Mat img2, vector<KeyPoint> keyImg1, vector<KeyPoint> keyImg2, int matchnum)
{
	Ptr<Feature2D> b = xfeatures2d::SIFT::create();

	Ptr<DescriptorMatcher> descriptorMatcher;

	// Match between img1 and img2
	vector<DMatch> matches;

	// Descriptor for img1 and img2
	Mat descImg1, descImg2;

	// and compute their descriptors with method  compute
	b->compute(img1, keyImg1, descImg1);
	b->compute(img1, keyImg2, descImg2);
	// Match method loop
	descriptorMatcher = DescriptorMatcher::create("BruteForce-L1");

	descriptorMatcher->match(descImg1, descImg2, matches, Mat());
	// Keep best matches only to have a nice drawing.
	// We sort distance between descriptor matches
	Mat index;
	int nbMatch = int(matches.size());
	Mat tab(nbMatch, 1, CV_32F);
	for (int i = 0; i<nbMatch; i++)
	{
		tab.at<float>(i, 0) = matches[i].distance;
	}
	sortIdx(tab, index, SORT_EVERY_COLUMN + SORT_ASCENDING);
	vector<DMatch> bestMatches;
	for (int i = 0; i<matchnum; i++)
	{
		bestMatches.push_back(matches[index.at<int>(i, 0)]);
	}
	Mat result;
	drawMatches(img1, keyImg1, img2, keyImg2, bestMatches, result);
	namedWindow("harris_sift_match", WINDOW_AUTOSIZE);
	imshow("harris_sift_match", result);


}
//角点检测
void on_GoodFeaturesToTrack(Mat &g_srcImage, vector<KeyPoint>& keypoints, int g_maxCornerNumber)
{
	Mat g_grayImage;
	RNG g_rng(12345);//初始化随机数生成器
	cvtColor(g_srcImage, g_grayImage, COLOR_BGR2GRAY);
	//【1】对变量小于等于1时的处理
	if (g_maxCornerNumber <= 1) { g_maxCornerNumber = 1; }
	//【2】Shi-Tomasi算法(goodFeaturesToTrack函数)的参数准备
	vector<Point2f> corners;
	double qualityLevel = 0.01;//角点检测可接受的最小特征值
	double minDistance = 10;//角点之间的最小距离
	int blockSize = 3;//计算导数自相关矩阵时指定的邻域范围
	double k = 0.04;//权重系数
	Mat copy = g_srcImage.clone();	//复制源图像到一个临时变量中,作为感兴趣区域

									//【3】进行Shi-Tomasi角点检测
	goodFeaturesToTrack(g_grayImage,//输入图像
		corners,//检测到的角点的输出向量
		g_maxCornerNumber,//角点的最大数量
		qualityLevel,//角点检测可接受的最小特征值
		minDistance,//角点之间的最小距离
		Mat(),//感兴趣区域
		blockSize,//计算导数自相关矩阵时指定的邻域范围
		false,//不使用Harris角点检测
		k);//权重系数

		   //【4】输出文字信息
	cout << "\n\t>-------------此次检测到的角点数量为:" << corners.size() << endl;
	//【5】绘制检测到的角点
	int r = 4;
	for (unsigned int i = 0; i < corners.size(); i++)
	{
		//以随机的颜色绘制出角点
		circle(g_srcImage, corners[i], r, Scalar(g_rng.uniform(0, 255), g_rng.uniform(0, 255),
			g_rng.uniform(0, 255)), 1, 8, 0);
	}
	//【6】显示(更新)窗口
	//imshow( WINDOW_NAME, copy );
	//【7】亚像素角点检测的参数设置
	Size winSize = Size(5, 5);
	Size zeroZone = Size(-1, -1);
	//此句代码的OpenCV2版为:
	//TermCriteria criteria = TermCriteria( CV_TERMCRIT_EPS + CV_TERMCRIT_ITER, 40, 0.001 );
	//此句代码的OpenCV3版为:
	TermCriteria criteria = TermCriteria(TermCriteria::EPS + TermCriteria::MAX_ITER, 40, 0.001);
	//【8】计算出亚像素角点位置
	cornerSubPix(g_grayImage, corners, winSize, zeroZone, criteria);
	//【9】输出角点信息
	// 	for( int i = 0; i < corners.size(); i++ )
	// 	{ cout<<" \t>>精确角点坐标["<<i<<"]  ("<<corners[i].x<<","<<corners[i].y<<")"<<endl; }
	KeyPoint::convert(corners, keypoints);

}
int main()
{
	Mat image01 = imread("1.jpg", 1);
	Mat image02 = imread("2.jpg", 1);
	if (image01.empty() || image02.empty()) {
		cout << "could not find the image..." << endl;
		return 0;
	}
	imshow("p1", image01);
	imshow("p2", image02);
	Mat copy1 = image01.clone();
	Mat copy2 = image02.clone();
	//harris角点检测
	std::vector<cv::KeyPoint> corners1, corners2;
	on_GoodFeaturesToTrack(image01, corners1, 100);
	on_GoodFeaturesToTrack(image02, corners2, 100);
	imshow("harimage01", image01);
	imshow("harimage02", image02);
	//角点检测后进行sift特征匹配
	int matchnum = corners1.size() > corners2.size() ? corners2.size() : corners1.size();
	harrismatch(copy1, copy2, corners1, corners2, matchnum);

	waitKey();
}

 

  • 1
    点赞
  • 19
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值