日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問(wèn) 生活随笔!

生活随笔

當(dāng)前位置: 首頁(yè) > 编程资源 > 编程问答 >内容正文

编程问答

TLD(Tracking-Learning-Detection)学习与源码理解之(五)

發(fā)布時(shí)間:2025/3/21 编程问答 21 豆豆
生活随笔 收集整理的這篇文章主要介紹了 TLD(Tracking-Learning-Detection)学习与源码理解之(五) 小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

TLD(Tracking-Learning-Detection)學(xué)習(xí)與源碼理解之(五)??

zouxy09@qq.com

http://blog.csdn.net/zouxy09

????

?????? 下面是自己在看論文和這些大牛的分析過(guò)程中,對(duì)代碼進(jìn)行了一些理解,但是由于自己接觸圖像處理和機(jī)器視覺(jué)沒(méi)多久,另外由于自己編程能力比較弱,所以分析過(guò)程可能會(huì)有不少的錯(cuò)誤,希望各位不吝指正。而且,因?yàn)榫幊毯芏嗟胤讲欢?#xff0c;所以注釋得非常亂,還海涵。

LKTracker.h

#include<tld_utils.h> #include <opencv2/opencv.hpp>//使用金字塔LK光流法跟蹤,所以類(lèi)的成員變量很多都是OpenCV中calcOpticalFlowPyrLK()函數(shù)的參數(shù) class LKTracker{ private:std::vector<cv::Point2f> pointsFB;cv::Size window_size; //每個(gè)金字塔層的搜索窗口尺寸int level; //最大的金字塔層數(shù)std::vector<uchar> status; //數(shù)組。如果對(duì)應(yīng)特征的光流被發(fā)現(xiàn),數(shù)組中的每一個(gè)元素都被設(shè)置為 1, 否則設(shè)置為 0std::vector<uchar> FB_status; std::vector<float> similarity; //相似度std::vector<float> FB_error; //Forward-Backward error方法,求FB_error的結(jié)果與原始位置的歐式距離//做比較,把距離過(guò)大的跟蹤結(jié)果舍棄float simmed;float fbmed;//TermCriteria模板類(lèi),取代了之前的CvTermCriteria,這個(gè)類(lèi)是作為迭代算法的終止條件的//該類(lèi)變量需要3個(gè)參數(shù),一個(gè)是類(lèi)型,第二個(gè)參數(shù)為迭代的最大次數(shù),最后一個(gè)是特定的閾值。//指定在每個(gè)金字塔層,為某點(diǎn)尋找光流的迭代過(guò)程的終止條件。cv::TermCriteria term_criteria;float lambda; //某閾值??Lagrangian 乘子// NCC 歸一化交叉相關(guān),FB error與NCC結(jié)合,使跟蹤更穩(wěn)定 交叉相關(guān)的圖像匹配算法??//交叉相關(guān)法的作用是進(jìn)行云團(tuán)移動(dòng)的短時(shí)預(yù)測(cè)。選取連續(xù)兩個(gè)時(shí)次的GMS-5衛(wèi)星云圖,將云圖區(qū)域劃分為32×32像素//的圖像子集,采用交叉相關(guān)法計(jì)算獲取兩幅云圖的最佳匹配區(qū)域,根據(jù)前后云圖匹配區(qū)域的位置和時(shí)間間隔,確//定出每個(gè)圖像子集的移動(dòng)矢量(速度和方向),并對(duì)圖像子集的移動(dòng)矢量進(jìn)行客觀分析,其后,基于檢驗(yàn)后的云//圖移動(dòng)矢量集,利用后向軌跡方法對(duì)云圖作短時(shí)外推預(yù)測(cè)。void normCrossCorrelation(const cv::Mat& img1, const cv::Mat& img2, std::vector<cv::Point2f>& points1, std::vector<cv::Point2f>& points2);bool filterPts(std::vector<cv::Point2f>& points1,std::vector<cv::Point2f>& points2); public:LKTracker();//特征點(diǎn)的跟蹤??bool trackf2f(const cv::Mat& img1, const cv::Mat& img2,std::vector<cv::Point2f> &points1, std::vector<cv::Point2f> &points2);float getFB(){return fbmed;} };


?

LKTracker.cpp

#include <LKTracker.h> using namespace cv;//金字塔LK光流法跟蹤 //Media Flow 中值光流跟蹤 加 跟蹤錯(cuò)誤檢測(cè) //構(gòu)造函數(shù),初始化成員變量 LKTracker::LKTracker(){該類(lèi)變量需要3個(gè)參數(shù),一個(gè)是類(lèi)型,第二個(gè)參數(shù)為迭代的最大次數(shù),最后一個(gè)是特定的閾值。term_criteria = TermCriteria( TermCriteria::COUNT + TermCriteria::EPS, 20, 0.03);window_size = Size(4,4);level = 5;lambda = 0.5; }bool LKTracker::trackf2f(const Mat& img1, const Mat& img2, vector<Point2f> &points1, vector<cv::Point2f> &points2){//TODO!:implement c function cvCalcOpticalFlowPyrLK() or Faster tracking function//Forward-Backward tracking//基于Forward-Backward Error的中值流跟蹤方法//金字塔LK光流法跟蹤//forward trajectory 前向軌跡跟蹤calcOpticalFlowPyrLK( img1,img2, points1, points2, status, similarity, window_size, level, term_criteria, lambda, 0);//backward trajectory 后向軌跡跟蹤calcOpticalFlowPyrLK( img2,img1, points2, pointsFB, FB_status,FB_error, window_size, level, term_criteria, lambda, 0);//Compute the real FB-error//原理很簡(jiǎn)單:從t時(shí)刻的圖像的A點(diǎn),跟蹤到t+1時(shí)刻的圖像B點(diǎn);然后倒回來(lái),從t+1時(shí)刻的圖像的B點(diǎn)往回跟蹤,//假如跟蹤到t時(shí)刻的圖像的C點(diǎn),這樣就產(chǎn)生了前向和后向兩個(gè)軌跡,比較t時(shí)刻中 A點(diǎn) 和 C點(diǎn) 的距離,如果距離//小于一個(gè)閾值,那么就認(rèn)為前向跟蹤是正確的;這個(gè)距離就是FB_error//計(jì)算 前向 與 后向 軌跡的誤差for( int i= 0; i<points1.size(); ++i ){FB_error[i] = norm(pointsFB[i]-points1[i]); //norm()求矩陣或向量的范數(shù)??絕對(duì)值?}//Filter out points with FB_error[i] <= median(FB_error) && points with sim_error[i] > median(sim_error)normCrossCorrelation(img1, img2, points1, points2);return filterPts(points1, points2); }//利用NCC把跟蹤預(yù)測(cè)的結(jié)果周?chē)?0*10的小圖片與原始位置周?chē)?0*10的小圖片(使用函數(shù)getRectSubPix得到)進(jìn) //行模板匹配(調(diào)用matchTemplate) void LKTracker::normCrossCorrelation(const Mat& img1,const Mat& img2, vector<Point2f>& points1, vector<Point2f>& points2) {Mat rec0(10,10,CV_8U);Mat rec1(10,10,CV_8U);Mat res(1,1,CV_32F);for (int i = 0; i < points1.size(); i++) {if (status[i] == 1) { //為1表示該特征點(diǎn)跟蹤成功//從前一幀和當(dāng)前幀圖像中(以每個(gè)特征點(diǎn)為中心?)提取10x10象素矩形,使用亞象素精度getRectSubPix( img1, Size(10,10), points1[i],rec0 ); getRectSubPix( img2, Size(10,10), points2[i],rec1);//匹配前一幀和當(dāng)前幀中提取的10x10象素矩形,得到匹配后的映射圖像//CV_TM_CCOEFF_NORMED 歸一化相關(guān)系數(shù)匹配法//參數(shù)分別為:欲搜索的圖像。搜索模板。比較結(jié)果的映射圖像。指定匹配方法matchTemplate( rec0,rec1, res, CV_TM_CCOEFF_NORMED); similarity[i] = ((float *)(res.data))[0]; //得到各個(gè)特征點(diǎn)的相似度大小} else {similarity[i] = 0.0;}}rec0.release();rec1.release();res.release(); }//篩選出 FB_error[i] <= median(FB_error) 和 sim_error[i] > median(sim_error) 的特征點(diǎn) //得到NCC和FB error結(jié)果的中值,分別去掉中值一半的跟蹤結(jié)果不好的點(diǎn) bool LKTracker::filterPts(vector<Point2f>& points1,vector<Point2f>& points2){//Get Error Medianssimmed = median(similarity); //找到相似度的中值size_t i, k;for( i=k = 0; i<points2.size(); ++i ){if( !status[i])continue;if(similarity[i]> simmed){ //剩下 similarity[i]> simmed 的特征點(diǎn)points1[k] = points1[i]; points2[k] = points2[i];FB_error[k] = FB_error[i];k++;}}if (k==0)return false;points1.resize(k);points2.resize(k);FB_error.resize(k);fbmed = median(FB_error); //找到FB_error的中值for( i=k = 0; i<points2.size(); ++i ){if( !status[i])continue;if(FB_error[i] <= fbmed){ /points1[k] = points1[i]; //再對(duì)上一步剩下的特征點(diǎn)進(jìn)一步篩選,剩下 FB_error[i] <= fbmed 的特征點(diǎn)points2[k] = points2[i];k++;}}points1.resize(k);points2.resize(k);if (k>0)return true;elsereturn false; }/** old OpenCV style void LKTracker::init(Mat img0, vector<Point2f> &points){//Preallocate//pyr1 = cvCreateImage(Size(img1.width+8,img1.height/3),IPL_DEPTH_32F,1);//pyr2 = cvCreateImage(Size(img1.width+8,img1.height/3),IPL_DEPTH_32F,1);//const int NUM_PTS = points.size();//status = new char[NUM_PTS];//track_error = new float[NUM_PTS];//FB_error = new float[NUM_PTS]; }void LKTracker::trackf2f(..){cvCalcOpticalFlowPyrLK( &img1, &img2, pyr1, pyr1, points1, points2, points1.size(), window_size, level, status, track_error, term_criteria, CV_LKFLOW_INITIAL_GUESSES);cvCalcOpticalFlowPyrLK( &img2, &img1, pyr2, pyr1, points2, pointsFB, points2.size(),window_size, level, 0, 0, term_criteria, CV_LKFLOW_INITIAL_GUESSES | CV_LKFLOW_PYR_A_READY | CV_LKFLOW_PYR_B_READY ); } */

總結(jié)

以上是生活随笔為你收集整理的TLD(Tracking-Learning-Detection)学习与源码理解之(五)的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。

如果覺(jué)得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。