两帧法匹配

由于在实际应用过程中,sift,surf等匹配方法很难达到实时匹配的效果要求,故而采用双帧法进行匹配,即目标图像与第一帧之间默认有较大差异,故此之间采用复杂匹配算法,而在此后视频播放过程中,默认帧与帧之间的变化程度不大,故此可以采用简单匹配算法以满足匹配的实时性要求。
此方法具体过程为:目标模板与第一帧采用复杂匹配算法,之后对匹配结果进行RANSAC方法求出两帧之间的基础变换矩阵H1。而第一帧与后面帧采用简单算法匹配,之后对匹配结果进行RANSAC方法求出两帧之间的基础变换矩阵H2.之后求出H3=H1*H2为目标模板与待匹配图像之间的基础变换矩阵H3.此方法不但可以解决匹配的实时性问题,而且抗干扰能力强,如若发生目标物体被遮挡等现象,我们仍旧可以通过变换矩阵来求出目标物体在待匹配图像上方的位置。具体实验方法与结果如下:

#include<opencv2\opencv.hpp>
#include <stdio.h>
#include <iostream>
#include "opencv2/core.hpp"
#include "opencv2/imgproc.hpp"
#include "opencv2/features2d.hpp"
#include "opencv2/highgui.hpp"
#include "opencv2/calib3d.hpp"
#include "opencv2/xfeatures2d.hpp"
#include<iostream>
using namespace std;
using namespace cv;
#define sizes 20
int x = 0;
int y = 0;
bool  match(Mat a,Mat b, vector<DMatch> &vec)
{
	BFMatcher matches;
	vector<DMatch>matcher;
	matches.match(a, b, matcher);
	vec = matcher;
	return 1;
}
Mat geth(vector<DMatch>&vec,vector<KeyPoint>&a,vector<KeyPoint>&b)
{
	Mat H;
	vector<Point>x, y;
	for (int i = 0; i < vec.size(); i++)
	{
		x.push_back(a.at(vec.at(i).queryIdx).pt);
		y.push_back(b.at(vec.at(i).trainIdx).pt);
	}
	H = findHomography(x, y, RANSAC);
	return H;
}
Mat Orb(Mat a, Mat b)
{
	vector<KeyPoint>keypoint1, keypoint2;
	Mat des1, des2;
	Mat result;
	Ptr<ORB>orb = ORB::create();
	orb->detect(a, keypoint1);
	orb->detect(b, keypoint2);
	orb->compute(a, keypoint1, des1);
	orb->compute(b, keypoint2, des2);
	vector<DMatch>vec;
	match(des1, des2, vec);
	result = geth(vec, keypoint1, keypoint2);
	return result;
}
Mat Sift(Mat a, Mat b)
{
	vector<KeyPoint>keypoint1, keypoint2;
	Mat des1, des2;
	Mat result;
	Ptr<Feature2D>sift = xfeatures2d::SIFT::create();
	sift->detect(a, keypoint1);
	sift->detect(b, keypoint2);
	sift->compute(a, keypoint1, des1);
	sift->compute(b, keypoint2, des2);
	vector<DMatch>vec;
	match(des1, des2, vec);
	result=geth(vec, keypoint1, keypoint2);
	return result;
}
Mat FastBreif(Mat &a, Mat &b)
{
	Mat des1, des2,result;
	vector<KeyPoint> keypoint1,keypoint2;//关键点KeyPoint类
    Ptr<FastFeatureDetector> fast = FastFeatureDetector::create();
	fast->detect(a, keypoint1);;
	fast->detect(b, keypoint2);
	Ptr<Feature2D>breif = xfeatures2d::BriefDescriptorExtractor::create();
	breif->compute(a, keypoint1, des1);
	breif->compute(b, keypoint2, des2);
	vector<DMatch>vec;
	match(des1, des2, vec);
	result = geth(vec, keypoint1, keypoint2);
	return result;
}
void printH(Mat &H)
{
	for (int i = 0; i < H.rows; i++)
	{
		for (int j = 0; j < H.cols; j++)
		{
			cout << H.at<double>(i, j) << " ";
		}
		cout << endl;
	}
}
void draw(Mat &a,int length,int width)
{
	line(a, cvPoint(length - sizes / 2, width), cvPoint(length + sizes / 2, width), Scalar(0, 0, 255), 5);
	line(a, cvPoint(length, width - sizes / 2), cvPoint(length, width + sizes / 2), Scalar(0, 0, 255), 5);
}
void sub(Mat &d,Mat &H,int c,int b)
{
	int z1, v1, q1;
	z1 = c * H.at<double>(0, 0) + b * H.at<double>(0, 1) + H.at<double>(0, 2);
	v1 = c * H.at<double>(1, 0) + b* H.at<double>(1, 1) + H.at<double>(1, 2);
	q1 = c * H.at<double>(2, 0) + b* H.at<double>(2, 1) + H.at<double>(2, 2);
	cout << z1 << "  " << v1 << "  " << q1 << endl;
	if (q1 != 0)
	{
		z1 = z1 / q1;
		v1 = v1 / q1;
	}
	x = z1;
	y = v1;
	draw(d, z1, v1);
}
void main()
{
	const int x1 = 518;
	const int y1 = 179;
	const int length_x = 250;
	const int width_y = 250;
	Mat img_1 = imread("7.jpg");
	VideoCapture capture("6.mp4");
	Mat img_2,img_3;
	capture >> img_2;
	for (int i = 0; i <40; i++)
	{
		capture >> img_3;
	}
	resize(img_3, img_3, Size(img_3.cols / 2, img_3.rows / 2), 0, 0, INTER_CUBIC);
	resize(img_2, img_2, Size(img_2.cols / 2, img_2.rows / 2), 0, 0, INTER_CUBIC);
	imwrite("8.jpg", img_2);
	imwrite("9.jpg", img_3);
	Mat img_4 = img_2.clone();
	Mat img_5 = img_1.clone();
	Mat img_6 = img_3.clone();
	Mat H1=Sift(img_1, img_2);
	//Mat H1 = Orb(img_1, img_2);
	printH(H1);
	draw(img_1,length_x,width_y);
	sub(img_2, H1, length_x, width_y);
	//
	Mat H2 = FastBreif(img_4, img_3);
	printH(H2);
	draw(img_4, x, y);
	sub(img_3, H2, x, y);
	//
	Mat H3 = H2*H1;
	printH(H3);
	draw(img_5, x1, y1);
	sub(img_6, H3, x1, y1);
	
	imshow("img_1", img_1);
	imshow("img_2", img_2);
	imshow("img_3", img_3);
	imshow("img_4", img_4);
	imshow("img_5", img_5);
	imshow("img_6", img_6);
	waitKey(0);
}

实验结果如下:
H矩阵与变换坐标为:
1.18139 -0.00914043 -120.436
0.0067695 1.17805 -62.865
6.55392e-006 -1.79877e-005 1
172 233 0
1.00411 0.000401082 -2.31253
0.000444301 1.00373 -1.31413
5.7269e-006 3.37023e-006 1
170 232 1
1.18624 -0.00866394 -123.269
0.00731099 1.18246 -64.4668
1.33424e-005 -1.40697e-005 0.999098
489 150 1

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值