You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

687 lines
17 KiB
C++

2 years ago
#include "stdafx.h"
#include "superResolutionImg.h"
// openCV Library
#include <opencv2/opencv.hpp>
#include "opencv2/nonfree/features2d.hpp"
using namespace cv;
#include <deque>
#include "fuseImg.h"
#include "histProject.h"
// <20>Ƴ<EFBFBD>NN<4E><4E><EFBFBD>ʴ<EFBFBD><CAB4><EFBFBD><EFBFBD><EFBFBD>ֵ<EFBFBD><D6B5>ƥ<EFBFBD><C6A5>
int ClearMatchByKnnRatio(std::vector<std::vector<cv::DMatch>> &matches, float ratio)
{
try
{
// <20>Ƴ<EFBFBD>ƥ<EFBFBD><C6A5><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ŀ
int removedCount = 0;
// <20><>ʼ<EFBFBD><CABC><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
std::vector<std::vector<cv::DMatch>>::iterator DMatchIterator = matches.begin();
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ƥ<EFBFBD><C6A5>
for (; DMatchIterator != matches.end(); ++DMatchIterator)
{
// <20><><EFBFBD><EFBFBD>ʶ<EFBFBD><CAB6><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
if (DMatchIterator->size() > 1)
{
// <20>ν<EFBFBD><CEBD><EFBFBD><EFBFBD><EFBFBD>
if ((*DMatchIterator)[1].distance > 0)
{
if ((*DMatchIterator)[0].distance / (*DMatchIterator)[1].distance > ratio)
{
DMatchIterator->clear();
removedCount++;
}
}
else
{
DMatchIterator->clear();
removedCount++;
}
}
else // <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
{
DMatchIterator->clear();
removedCount++;
}
} // end of for
return removedCount;
}
catch(cv::Exception &e)
{
e.msg;
return 0;
}
catch(...)
{
return 0;
}
}
// <20><>ȡ<EFBFBD>Գ<EFBFBD>ƥ<EFBFBD><C6A5>
int GetSysmmetryMatch(std::vector<cv::DMatch> &sysmMatches,
const std::vector<std::vector<cv::DMatch>> &preMatches,
const std::vector<std::vector<cv::DMatch>> &nextMatches)
{
try
{
sysmMatches.clear();
// <20>Գ<EFBFBD>ƥ<EFBFBD><C6A5><EFBFBD><EFBFBD>Ŀ
int sysmMatchNum = 0;
// <20><><EFBFBD><EFBFBD>matches1<73><31><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ƥ<EFBFBD><C6A5>
std::vector<std::vector<cv::DMatch>>::const_iterator preMatchesIterator = preMatches.begin();
for(; preMatchesIterator != preMatches.end(); preMatchesIterator++)
{
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ɾ<EFBFBD><C9BE><EFBFBD><EFBFBD>ƥ<EFBFBD><C6A5>
if (preMatchesIterator->size() < 2)
{
continue;
}
// <20><><EFBFBD><EFBFBD>matches2<73><32><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ƥ<EFBFBD><C6A5>
std::vector<std::vector<cv::DMatch>>::const_iterator nextMatchesIterator = nextMatches.begin();
for(; nextMatchesIterator != nextMatches.end(); nextMatchesIterator++)
{
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ɾ<EFBFBD><C9BE><EFBFBD><EFBFBD>ƥ<EFBFBD><C6A5>
if (nextMatchesIterator->size() < 2)
{
continue;
}
if ((*preMatchesIterator)[0].queryIdx == (*nextMatchesIterator)[0].trainIdx
&& (*preMatchesIterator)[0].trainIdx == (*nextMatchesIterator)[0].queryIdx)
{
// <20><><EFBFBD>ӶԳ<D3B6>ƥ<EFBFBD><C6A5>
sysmMatches.push_back(cv::DMatch((*preMatchesIterator)[0].queryIdx, (*preMatchesIterator)[0].trainIdx, (*preMatchesIterator)[0].distance));
sysmMatchNum++;
break;
}
}
}
// <20><><EFBFBD>ضԳ<D8B6>ƥ<EFBFBD><C6A5><EFBFBD><EFBFBD>Ŀ
return sysmMatchNum;
}
catch(cv::Exception &e)
{
e.msg;
return 0;
}
catch(...)
{
return 0;
}
}
// <20><><EFBFBD>ڡ<EFBFBD><DAA1>Լ<EFBFBD>Լ<EFBFBD><D4BC><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>µ<EFBFBD><C2B5><EFBFBD><EFBFBD><EFBFBD>ƥ<EFBFBD><C6A5>ʶ<EFBFBD><CAB6><EFBFBD><EFBFBD><EFBFBD>õ<EFBFBD>RANSAC<41><43><EFBFBD>Ʒ<EFBFBD><C6B7><EFBFBD><EFBFBD><EFBFBD>
bool GetRansacBaseMatch(std::vector<cv::DMatch> &ransacMatches,
std::vector<cv::Point2f> &prePts,
std::vector<cv::Point2f> &nextPts,
const std::vector<cv::DMatch> &matches,
const std::vector<cv::KeyPoint> &preKeyPts,
const std::vector<cv::KeyPoint> &nextKeyPts)
{
try
{
// <20><><EFBFBD><EFBFBD><EFBFBD>ж<EFBFBD> <20>Լ<EFBFBD>Լ<EFBFBD><D4BC><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ҫ8<D2AA><38><EFBFBD><EFBFBD><EFBFBD><EFBFBD>,
if (matches.size() > preKeyPts.size() || matches.size() > nextKeyPts.size() || matches.size() < 12)
{
return false;
}
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
ransacMatches.clear();
prePts.clear();
nextPts.clear();
// ת<><D7AA>KeyPoint<6E><74><EFBFBD>͵<EFBFBD>Point2f
std::vector<DMatch>::const_iterator it = matches.begin();
for(; it != matches.end(); it++)
{
// <20>õ<EFBFBD><C3B5><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
prePts.push_back(preKeyPts[it->queryIdx].pt);
// <20>õ<EFBFBD><C3B5>ұ<EFBFBD><D2B1><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
nextPts.push_back(nextKeyPts[it->trainIdx].pt);
}
// <20><><EFBFBD><EFBFBD>RANSAC<41><43><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
std::vector<unsigned char> inliers(prePts.size(), 0);
cv::Mat fundementalMat; // <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
fundementalMat = cv::findFundamentalMat(cv::Mat(prePts), // <20><><EFBFBD><EFBFBD>ƥ<EFBFBD><C6A5><EFBFBD>㼯1
cv::Mat(nextPts), // <20><><EFBFBD><EFBFBD>ƥ<EFBFBD><C6A5><EFBFBD>㼯2
inliers, // <20><><EFBFBD><EFBFBD>ƥ<EFBFBD><C6A5>״̬ outlier(0) inlier(1)
CV_FM_RANSAC, // RANSAC<41><43><EFBFBD><EFBFBD>
3.0, // <20><><EFBFBD><EFBFBD><EFBFBD>ߵľ<DFB5><C4BE><EFBFBD>
0.99); // <20><><EFBFBD>Ÿ<EFBFBD><C5B8><EFBFBD>
// <20><>ȡͨ<C8A1><CDA8><EFBFBD><EFBFBD>ƥ<EFBFBD><C6A5>
std::vector<unsigned char>::const_iterator itInliers = inliers.begin();
std::vector<cv::DMatch>::const_iterator itMatches = matches.begin();
for (; itInliers != inliers.end(); ++itInliers,++itMatches)
{
if (*itInliers) // <20><>Чƥ<D0A7><C6A5>
{
ransacMatches.push_back((*itMatches));
}
}
// <20><><EFBFBD>ݽ<EFBFBD><DDBD>յ<EFBFBD>ƥ<EFBFBD><EFBFBD><E4A3AC><EFBFBD>¼<EFBFBD><C2BC><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>fundementalMat
prePts.clear();
nextPts.clear();
std::vector<DMatch>::const_iterator itRansacMatches = ransacMatches.begin();
for(; itRansacMatches != ransacMatches.end(); ++itRansacMatches)
{
// <20>õ<EFBFBD><C3B5><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
prePts.push_back(preKeyPts[itRansacMatches->queryIdx].pt);
// <20>õ<EFBFBD><C3B5>ұ<EFBFBD><D2B1><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
nextPts.push_back(nextKeyPts[itRansacMatches->trainIdx].pt);
}
return true;
}
catch(cv::Exception &e)
{
e.msg;
return false;
}
catch(...)
{
return false;
}
}
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>С<EFBFBD><D0A1><EFBFBD>˼<EFBFBD><CBBC><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><E4BBBB><EFBFBD><EFBFBD>
bool GetAffineTransMat(cv::Mat &result,
const std::vector<Point2f> &prePoints,
const std::vector<Point2f> &nextPoints)
{
try
{
int preSize = prePoints.size();
int nextSize = nextPoints.size();
if (preSize < 3 || nextSize < 3 || preSize != nextSize)
{
return false;
}
// <20><><EFBFBD>·<EFBFBD><C2B7><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
result.create(3, 3, CV_64FC1);
result = cv::Scalar(0);
// ƥ<><C6A5><EFBFBD><EFBFBD>Ŀ
int MatchNum = preSize;
/* set up matrices so we can unstack homography into X; AX = B */
cv::Mat A(2 * MatchNum, 6, CV_64FC1);
cv::Mat B(2 * MatchNum, 1, CV_64FC1);
cv::Mat X(6, 1, CV_64FC1);
// <20><><EFBFBD><EFBFBD>
A = cv::Scalar(0);
B = cv::Scalar(0);
X = cv::Scalar(0);
// <20><>ʼ<EFBFBD><CABC><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
for(int i = 0; i < MatchNum; i++ )
{
A.at<double>(i, 0) = prePoints[i].x;
A.at<double>(i, 1) = prePoints[i].y;
A.at<double>(i, 2) = 1.0f;
A.at<double>(i + MatchNum, 3) = prePoints[i].x;
A.at<double>(i + MatchNum, 4) = prePoints[i].y;
A.at<double>(i + MatchNum, 5) = 1.0f;
B.at<double>(i, 0) = nextPoints[i].x;
B.at<double>(i + MatchNum, 0) = nextPoints[i].y;
}
// <20><EFBFBD><E2B7BD>
cv::solve(A, B, X, CV_SVD);
// <20><>ֵ
result.at<double>(0, 0) = X.at<double>(0, 0);
result.at<double>(0, 1) = X.at<double>(1, 0);
result.at<double>(0, 2) = X.at<double>(2, 0);
result.at<double>(1, 0) = X.at<double>(3, 0);
result.at<double>(1, 1) = X.at<double>(4, 0);
result.at<double>(1, 2) = X.at<double>(5, 0);
result.at<double>(2, 0) = 0.0;
result.at<double>(2, 1) = 0.0;
result.at<double>(2, 2) = 1.0;
return true;
}
catch(cv::Exception &e)
{
e.msg;
return false;
}
catch(...)
{
return false;
}
}
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>С<EFBFBD><D0A1><EFBFBD>˼<EFBFBD><CBBC><EFBFBD>͸<EFBFBD>ӱ任<D3B1><E4BBBB><EFBFBD><EFBFBD>
bool GetPerpectTransMat(cv::Mat &result,
const std::vector<Point2f> &prePoints,
const std::vector<Point2f> &nextPoints)
{
try
{
int preSize = prePoints.size();
int nextSize = nextPoints.size();
if (preSize < 4 || nextSize < 4 || preSize != nextSize)
{
return false;
}
// <20><><EFBFBD>·<EFBFBD><C2B7><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
result.create(3, 3, CV_64FC1);
result = cv::Scalar(0);
// ƥ<><C6A5><EFBFBD><EFBFBD>Ŀ
int MatchNum = nextSize;
/* set up matrices so we can unstack homography into X; AX = B */
cv::Mat A(2 * MatchNum, 8, CV_64FC1);
cv::Mat B(2 * MatchNum, 1, CV_64FC1);
cv::Mat X(8, 1, CV_64FC1);
// <20><><EFBFBD><EFBFBD>
A = cv::Scalar(0);
B = cv::Scalar(0);
X = cv::Scalar(0);
// <20><>ʼ<EFBFBD><CABC><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
for(int i = 0; i < MatchNum; i++ )
{
A.at<double>(i, 0) = prePoints[i].x;
A.at<double>(i, 1) = prePoints[i].y;
A.at<double>(i, 2) = 1.0f;
A.at<double>(i, 6) = -prePoints[i].x * nextPoints[i].x;
A.at<double>(i, 7) = -prePoints[i].y * nextPoints[i].x;
A.at<double>(i + MatchNum, 3) = prePoints[i].x;
A.at<double>(i + MatchNum, 4) = prePoints[i].y;
A.at<double>(i + MatchNum, 5) = 1.0f;
A.at<double>(i + MatchNum, 6) = -prePoints[i].x * nextPoints[i].y;
A.at<double>(i + MatchNum, 7) = -prePoints[i].y * nextPoints[i].y;
B.at<double>(i, 0) = nextPoints[i].x;
B.at<double>(i + MatchNum, 0) = nextPoints[i].y;
}
// <20><EFBFBD><E2B7BD>
cv::solve(A, B, X, CV_SVD);
// <20><>ֵ
result.at<double>(0, 0) = X.at<double>(0, 0);
result.at<double>(0, 1) = X.at<double>(1, 0);
result.at<double>(0, 2) = X.at<double>(2, 0);
result.at<double>(1, 0) = X.at<double>(3, 0);
result.at<double>(1, 1) = X.at<double>(4, 0);
result.at<double>(1, 2) = X.at<double>(5, 0);
result.at<double>(2, 0) = X.at<double>(6, 0);
result.at<double>(2, 1) = X.at<double>(7, 0);
result.at<double>(2, 2) = 1.0;
return true;
}
catch(cv::Exception &e)
{
e.msg;
return false;
}
catch(...)
{
return false;
}
}
// <20><><EFBFBD><EFBFBD>ͼ<EFBFBD><CDBC><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ƥ<EFBFBD><EFBFBD><E4A3AC><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ϵ
void CalImgAdjacentMat(std::deque<cv::Mat> &adjacentMatDeque,
std::deque<int> &successTagDeque,
const std::deque<std::vector<cv::KeyPoint>> &imgKeyptsDeque,
const std::deque<cv::Mat> &imgDescriptorsDeque)
{
if (imgKeyptsDeque.empty() == true
|| imgDescriptorsDeque.empty() == true
|| imgKeyptsDeque.size() != imgDescriptorsDeque.size())
{
return;
}
adjacentMatDeque.clear();
successTagDeque.clear();
// <20><><EFBFBD><EFBFBD>Ŀ
size_t count = imgKeyptsDeque.size();
for (size_t i = 0; i < (count - 1); i++)
{
// Flannƥ<6E><C6A5><EFBFBD><EFBFBD>
cv::FlannBasedMatcher matcher;
std::vector<cv::KeyPoint> preImgKeypts = imgKeyptsDeque.at(i);
std::vector<cv::KeyPoint> nextImgKeypts = imgKeyptsDeque.at(i + 1);
cv::Mat preImgDescriptors = imgDescriptorsDeque.at(i);
cv::Mat nextImgDescriptors = imgDescriptorsDeque.at(i + 1);
// <20><><EFBFBD><EFBFBD>ƥ<EFBFBD><C6A5><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
std::vector<std::vector<cv::DMatch>> Pre2NextMatches;
std::vector<std::vector<cv::DMatch>> Next2PreMatches;
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>/<2F>ν<EFBFBD><CEBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ƥ<EFBFBD><C6A5>
matcher.knnMatch(preImgDescriptors, nextImgDescriptors, Pre2NextMatches, 2); // ǰ<><C7B0>ƥ<EFBFBD><C6A5>
matcher.knnMatch(nextImgDescriptors, preImgDescriptors, Next2PreMatches, 2); // <20><><EFBFBD><EFBFBD>ƥ<EFBFBD><C6A5>
// <20>޳<EFBFBD><DEB3><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ƥ<EFBFBD><C6A5>
ClearMatchByKnnRatio(Pre2NextMatches, 0.65f);
ClearMatchByKnnRatio(Next2PreMatches, 0.65f);
// <20>Գ<EFBFBD>ƥ<EFBFBD><C6A5>
vector<DMatch> SysmMatches;
GetSysmmetryMatch(SysmMatches,
Pre2NextMatches,
Next2PreMatches);
// Ransac<61><63><EFBFBD>Լ<EFBFBD>Լ<EFBFBD><D4BC><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ƥ<EFBFBD><C6A5>
std::vector<cv::DMatch> RansacMatches;
std::vector<Point2f> PrePoints;
std::vector<Point2f> NextPoints;
bool MatchResult = false;
MatchResult = GetRansacBaseMatch(RansacMatches, // Ransacƥ<63><C6A5>
PrePoints,
NextPoints,
SysmMatches, // <20>Գ<EFBFBD>ƥ<EFBFBD><C6A5>
preImgKeypts,
nextImgKeypts);
if (MatchResult == false)
{
adjacentMatDeque.push_back(cv::Mat());
successTagDeque.push_back(0);
continue;
}
// <20><>֡ͼ<D6A1><CDBC><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ӿ<EFBFBD><D3BE><EFBFBD>
bool TransResult = false;
cv::Mat AdjacentMat;
TransResult = GetPerpectTransMat(AdjacentMat, PrePoints, NextPoints);
if (TransResult == false)
{
adjacentMatDeque.push_back(cv::Mat());
successTagDeque.push_back(0);
continue;
}
else
{
adjacentMatDeque.push_back(AdjacentMat);
successTagDeque.push_back(1);
}
}
}
// <20>Ҷ<EFBFBD>ͼ<EFBFBD>񣨺<EFBFBD><F1A3A8BA><EFBFBD>ͼ<EFBFBD>񣩳<EFBFBD><F1A3A9B3>ֱ<EFBFBD><D6B1>ʹ<EFBFBD><CAB9><EFBFBD>
int SuperResolutionImg(cv::Mat &dst, const std::deque<cv::Mat> &imgDeque, double multiple)
{
if (imgDeque.size() < 2)
{
return 0;
}
// <20><><EFBFBD>ֱ<EFBFBD><D6B1><EFBFBD>
if (multiple < 1)
{
multiple = 1;
}
else
if (multiple > 2)
{
multiple = 2;
}
// <20><>׼ <20><>0<EFBFBD><30>ͼ<EFBFBD><CDBC>
cv::Size imgSize = imgDeque[0].size();
for (size_t i = 0; i < imgDeque.size(); i++)
{
if (imgDeque[i].type() != CV_8UC1 || imgDeque[i].size() != imgSize) // <20>ߴ<EFBFBD><DFB4><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ж<EFBFBD>
{
return 0;
}
}
// ͼ<><CDBC><EFBFBD><EFBFBD><EFBFBD><EFBFBD>һ<EFBFBD><D2BB><EFBFBD><EFBFBD><EFBFBD>ļ<EFBFBD><C4BC><EFBFBD>
std::deque<cv::Mat> imgUpSampleDeque;
for (size_t i = 0; i < imgDeque.size(); i++)
{
// <20>ߴ<EFBFBD><DFB4>ӱ<EFBFBD>
cv::Mat upSampleImg;
cv::resize(imgDeque.at(i), upSampleImg, cv::Size(int(imgDeque.at(i).cols * multiple), int(imgDeque.at(i).rows * multiple)), 0, 0, 1);
imgUpSampleDeque.push_back(upSampleImg);
}
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
std::deque<std::vector<cv::KeyPoint>> imgKeyptsDeque;
std::deque<cv::Mat> imgDescriptorsDeque;
cv::SIFT sift(0, 3, 0.004); // С<><D0A1>ֵ
for (size_t i = 0; i < imgUpSampleDeque.size(); i++)
{
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
std::vector<cv::KeyPoint> imgKeypts;
cv::Mat imgDescriptors;
sift(imgUpSampleDeque.at(i), noArray(), imgKeypts, imgDescriptors, false);
// <20><><EFBFBD><EFBFBD>
imgKeyptsDeque.push_back(imgKeypts);
imgDescriptorsDeque.push_back(imgDescriptors);
}
// ͼ<><CDBC><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ƥ<EFBFBD><C6A5>
std::deque<cv::Mat> adjacentMatDeque;
std::deque<int> successTagDeque;
CalImgAdjacentMat(adjacentMatDeque, successTagDeque, imgKeyptsDeque, imgDescriptorsDeque);
// ѡ<><D1A1><EFBFBD><EFBFBD><EFBFBD>ѵ<EFBFBD>һ<EFBFBD><D2BB><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
std::deque<int> segment;
for (size_t i = 0; i < successTagDeque.size(); i++)
{
int count = 0;
for (size_t t = i; t < successTagDeque.size(); t++)
{
if (successTagDeque.at(t) == 1)
{
count++;
}
else
{
break;
}
}
segment.push_back(count);
}
// <20>ҳ<EFBFBD><D2B3><EFBFBD><EFBFBD><EFBFBD>ֵ<EFBFBD><D6B5><EFBFBD><EFBFBD>λ<EFBFBD><CEBB>
std::deque<int> segmentCopy = segment;
std::sort(segmentCopy.begin(), segmentCopy.end());
int maxVal = segmentCopy.at(segmentCopy.size() - 1);
// <20><><EFBFBD><EFBFBD>3<EFBFBD><33>ͼ<EFBFBD><CDBC>
if (maxVal < 2)
{
return 0;
}
int location = 0; // λ<><CEBB>
for (size_t i = 0; i < segment.size(); i++)
{
if (maxVal == segment.at(i))
{
location = i;
break;
}
}
// <20>ں<EFBFBD>ȫ<EFBFBD><C8AB><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
if (maxVal == static_cast<int>(successTagDeque.size()))
{
// ͼ<><CDBC>ϸ<EFBFBD><CFB8><EFBFBD><EFBFBD>ǿ
for (size_t i = 0; i < imgUpSampleDeque.size(); i++)
{
cv::Mat img;
imgUpSampleDeque[i].copyTo(img);
GNRHP(img, imgUpSampleDeque[i]);
}
// <20><><EFBFBD><EFBFBD><EFBFBD>ں<EFBFBD>
for (int i = imgUpSampleDeque.size() - 2; i > -1; i--)
{
cv::Mat img_pre = imgUpSampleDeque[i];
cv::Mat img_next = imgUpSampleDeque[i+1];
cv::Mat img_preNext;
img_pre.copyTo(img_preNext);
// <20><>֡ͼ<D6A1><CDBC><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ӿ<EFBFBD><D3BE><EFBFBD>
cv::Mat m_AdjacentMat = adjacentMatDeque[i];
// <20><><EFBFBD><EFBFBD>next <20>滻 pre ͼ<><CDBC>
double a00 = m_AdjacentMat.at<double>(0, 0);
double a01 = m_AdjacentMat.at<double>(0, 1);
double a02 = m_AdjacentMat.at<double>(0, 2);
double a10 = m_AdjacentMat.at<double>(1, 0);
double a11 = m_AdjacentMat.at<double>(1, 1);
double a12 = m_AdjacentMat.at<double>(1, 2);
double a20 = m_AdjacentMat.at<double>(2, 0);
double a21 = m_AdjacentMat.at<double>(2, 1);
double a22 = m_AdjacentMat.at<double>(2, 2);
for(int r = 0; r < img_preNext.rows; r++)
{
// #pragma omp parallel for
for (int c = 0; c < img_preNext.cols; c++)
{
double denominator = c * a20 + r * a21 + a22;
double src_x = (c * a00 + r * a01 + a02) / denominator;
double src_y = (c * a10 + r * a11 + a12) / denominator;
// <20><><EFBFBD><EFBFBD><EFBFBD>ڣ<EFBFBD><DAA3>ٶȿ<D9B6>
int x_nearest = int(src_x + 0.5);
int y_nearest = int(src_y + 0.5);
if ( x_nearest >= 0 && y_nearest >= 0 && x_nearest < img_next.cols && y_nearest < img_next.rows)
{
img_preNext.at<unsigned char>(r, c) = img_next.at<unsigned char>(y_nearest, x_nearest);
}
}
} // <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ؽ<EFBFBD><D8BD><EFBFBD>
// <20>ں<EFBFBD> img_pre <20><> img_preNext
cv::Mat fusion;
FuseImg(fusion, img_pre, img_preNext, "sym4", 10);
// <20><> fusion <20>滻 validImgUpSampleDeque[i]
fusion.copyTo(imgUpSampleDeque[i]);
}
imgUpSampleDeque[0].copyTo(dst);
return imgUpSampleDeque.size();
}
else
{
// ѡ<><D1A1><EFBFBD><EFBFBD>Ч<EFBFBD><D0A7>ͼ<EFBFBD><CDBC>Ƭ<EFBFBD><C6AC>
std::deque<cv::Mat> validImgUpSampleDeque(imgUpSampleDeque.begin() + location, imgUpSampleDeque.begin() + location + maxVal + 1);
// ͼ<><CDBC>ϸ<EFBFBD><CFB8><EFBFBD><EFBFBD>ǿ
for (size_t i = 0; i < validImgUpSampleDeque.size(); i++)
{
cv::Mat img;
validImgUpSampleDeque[i].copyTo(img);
GNRHP(img, validImgUpSampleDeque[i]);
}
std::deque<cv::Mat> validAdjacentMatDeque(adjacentMatDeque.begin() + location, adjacentMatDeque.begin() + location + maxVal);
imgUpSampleDeque.clear();
adjacentMatDeque.clear();
// <20><><EFBFBD><EFBFBD><EFBFBD>ں<EFBFBD>
for (int i = validImgUpSampleDeque.size() - 2; i > -1; i--)
{
cv::Mat img_pre = validImgUpSampleDeque[i];
cv::Mat img_next = validImgUpSampleDeque[i+1];
cv::Mat img_preNext;
img_pre.copyTo(img_preNext);
// <20><>֡ͼ<D6A1><CDBC><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ӿ<EFBFBD><D3BE><EFBFBD>
cv::Mat m_AdjacentMat = validAdjacentMatDeque[i];
// <20><><EFBFBD><EFBFBD>next <20>滻 pre ͼ<><CDBC>
double a00 = m_AdjacentMat.at<double>(0, 0);
double a01 = m_AdjacentMat.at<double>(0, 1);
double a02 = m_AdjacentMat.at<double>(0, 2);
double a10 = m_AdjacentMat.at<double>(1, 0);
double a11 = m_AdjacentMat.at<double>(1, 1);
double a12 = m_AdjacentMat.at<double>(1, 2);
double a20 = m_AdjacentMat.at<double>(2, 0);
double a21 = m_AdjacentMat.at<double>(2, 1);
double a22 = m_AdjacentMat.at<double>(2, 2);
for(int r = 0; r < img_preNext.rows; r++)
{
// #pragma omp parallel for
for (int c = 0; c < img_preNext.cols; c++)
{
double denominator = c * a20 + r * a21 + a22;
double src_x = (c * a00 + r * a01 + a02) / denominator;
double src_y = (c * a10 + r * a11 + a12) / denominator;
// <20><><EFBFBD><EFBFBD><EFBFBD>ڣ<EFBFBD><DAA3>ٶȿ<D9B6>
int x_nearest = int(src_x + 0.5);
int y_nearest = int(src_y + 0.5);
if ( x_nearest >= 0 && y_nearest >= 0 && x_nearest < img_next.cols && y_nearest < img_next.rows)
{
img_preNext.at<unsigned char>(r, c) = img_next.at<unsigned char>(y_nearest, x_nearest);
}
}
} // <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ؽ<EFBFBD><D8BD><EFBFBD>
// <20>ں<EFBFBD> img_pre <20><> img_preNext
cv::Mat fusion;
FuseImg(fusion, img_pre, img_preNext, "sym4", 10);
// <20><> fusion <20>滻 validImgUpSampleDeque[i]
fusion.copyTo(validImgUpSampleDeque[i]);
}
validImgUpSampleDeque[0].copyTo(dst);
return validImgUpSampleDeque.size();
}
}