当前位置: 首页 > 编程日记 > 正文

ORB_SLAM2中Tracking线程的三种追踪方式

1、参考关键帧追踪模式

bool Tracking::TrackReferenceKeyFrame()

对参考关键帧中的路标点进行跟踪。在Tracking线程中,每传入一帧,都会进行位姿优化。
  以上一帧的位姿为当前位姿进行优化。
(1)计算当前帧的词袋

mCurrentFrame.ComputeBoW();

(2)通过词袋加速算法,获得当前帧的特征点与参考帧的路标点间的联系。当匹配数小于15时,退出。

    // Step 2:通过特征点的BoW加快当前帧与参考帧之间的特征点匹配// 特征点的匹配关系由MapPoints进行维护int nmatches = matcher.SearchByBoW(mpReferenceKF,          //参考关键帧mCurrentFrame,          //当前帧vpMapPointMatches);     //存储匹配关系//这里的匹配数超过15才继续if(nmatches<15)return false;

(3)以上一帧的位姿为当前位姿,通过重投影误差进行优化

mCurrentFrame.mvpMapPoints = vpMapPointMatches;
mCurrentFrame.SetPose(mLastFrame.mTcw); // 用上一次的Tcw设置初值,在PoseOptimization可以收敛快一些
// Step 4:通过优化3D-2D的重投影误差来获得位姿Optimizer::PoseOptimization(&mCurrentFrame);

(4)删除外点
  根据BA优化的结果,判断那些点是外点。如果是外点的话,就删除其痕迹:路标点的指针置为NULL等。如果是内点的话,计数器加一。

	int nmatchesMap = 0;for(int i =0; i<mCurrentFrame.N; i++){if(mCurrentFrame.mvpMapPoints[i]){//如果对应到的某个特征点是外点if(mCurrentFrame.mvbOutlier[i]){//清除它在当前帧中存在过的痕迹MapPoint* pMP = mCurrentFrame.mvpMapPoints[i];mCurrentFrame.mvpMapPoints[i]=static_cast<MapPoint*>(NULL);mCurrentFrame.mvbOutlier[i]=false;pMP->mbTrackInView = false;pMP->mnLastFrameSeen = mCurrentFrame.mnId;nmatches--;}else if(mCurrentFrame.mvpMapPoints[i]->Observations()>0)//匹配的内点计数++nmatchesMap++;}}

(4)如果内点的数目大于10的话,返回追踪成功。此时当前帧的位姿已经被优化。
在这里插入图片描述

2、恒速运动模型

bool Tracking::TrackWithMotionModel

&emps;根据前两帧的运动估计当前帧的位姿,作为优化初值。

在这里插入图片描述(1)更新上一帧位姿。如果是双目、RGB-D相机的话,还会将未创建为地图点的三维点(双目相机可获得深度信息)作为临时地图点加入到地图中。

UpdateLastFrame();

(2)根据恒速运动模型获得当前帧的位姿。mVelocity为估计的上一帧到当前帧的位姿变换Tcl。Tcl*Tlw=Tcw

mCurrentFrame.SetPose(mVelocity*mLastFrame.mTcw);

(3)根据上一帧特征点对应地图点进行投影匹配,返回匹配上的个数。
(4)如果匹配个数不够的话,扩大搜索半径。如果匹配个数(特征点-特征点的联系、特征点-路标点的联系含义是一样的)还不够,直接返回。
(4)仅优化位姿。
(5)去除外点,根据剩余的匹配数量,返回是否匹配成功。追踪模式的要求更加严格(个人认为是追踪模式只有位姿约束,因此需要更多的位姿进行约束。)。

重定位(最后的拯救措施)

以PNP估计结果作为优化初值。

在这里插入图片描述(1)使用词袋模型找到当前帧的相似关键帧集合

    mCurrentFrame.ComputeBoW();// Relocalization is performed when tracking is lost// Track Lost: Query KeyFrame Database for keyframe candidates for relocalisation// Step 2:找到与当前帧相似的候选关键帧组vector<KeyFrame*> vpCandidateKFs = mpKeyFrameDB->DetectRelocalizationCandidates(&mCurrentFrame);// 如果没有候选关键帧,则退出if(vpCandidateKFs.empty())return false;

(2)使用ORB特征点检测候选关键帧,对合适的关键帧进行优化
vvpMapPointMatches:存放当前帧对每个关键帧成功匹配上的路标点的数量。
vbDiscarded:某个候选关键帧是否要放弃。
1)使用词袋快速匹配,匹配成功数量小于15的话,直接放弃

            int nmatches = matcher.SearchByBoW(pKF,mCurrentFrame,vvpMapPointMatches[i]);// 如果和当前帧的匹配数小于15,那么只能放弃这个关键帧if(nmatches<15){vbDiscarded[i] = true;continue;}

2)对匹配的路标点数目大于15的每个候选关键帧,设置pnp求解参数

				// 参数为当前帧、当前帧的特征点索引---->路标点PnPsolver* pSolver = new PnPsolver(mCurrentFrame,vvpMapPointMatches[i]);pSolver->SetRansacParameters(0.99,   //用于计算RANSAC迭代次数理论值的概率10,     //最小内点数, 但是要注意在程序中实际上是min(给定最小内点数,最小集,内点数理论值),不一定使用这个300,    //最大迭代次数4,      //最小集(求解这个问题在一次采样中所需要采样的最少的点的个数,对于Sim3是3,EPnP是4),参与到最小内点数的确定过程中0.5,    //这个是表示(最小内点数/样本总数);实际上的RANSAC正常退出的时候所需要的最小内点数其实是根据这个量来计算得到的5.991); // 自由度为2的卡方检验的阈值,程序中还会根据特征点所在的图层对这个阈值进行缩放vpPnPsolvers[i] = pSolver;nCandidates++;

(3)遍历候选关键帧,进行RANSAC+EPNP迭代估计相机位姿。

            // Step 4.1:通过EPnP算法估计姿态,迭代5次PnPsolver* pSolver = vpPnPsolvers[i];// 获得初步估计的相机位姿cv::Mat Tcw = pSolver->iterate(5,bNoMore,vbInliers,nInliers);

(4)对每个候选关键帧的位姿进行优化

int nGood = Optimizer::PoseOptimization(&mCurrentFrame);

(5)如果匹配到的内点数目不够,则将参考关键帧中的地图点投影至当前帧中,形成新的匹配。如果够了的话,直接结束循环。

之前是通过词袋加速算法获得了当前帧中的匹配到的路标点,会有遗漏。这里将参考关键帧中的所有路标点再次进行投影
(6)再次进行优化

nGood = Optimizer::PoseOptimization(&mCurrentFrame);

(7)如果不行的话,再用严格的标准投影一遍

                        if(nGood>30 && nGood<50){// 用更小窗口、更严格的描述子阈值,重新进行投影搜索匹配sFound.clear();for(int ip =0; ip<mCurrentFrame.N; ip++)if(mCurrentFrame.mvpMapPoints[ip])sFound.insert(mCurrentFrame.mvpMapPoints[ip]);nadditional =matcher2.SearchByProjection(mCurrentFrame,          //当前帧vpCandidateKFs[i],      //候选的关键帧sFound,                 //已经找到的地图点,不会用于PNP3,                      //新的窗口阈值,会乘以金字塔尺度64);                    //匹配的ORB描述子距离应该小于这个阈值// Final optimization// 如果成功挽救回来,匹配数目达到要求,最后BA优化一下if(nGood+nadditional>=50){nGood = Optimizer::PoseOptimization(&mCurrentFrame);//更新地图点for(int io =0; io<mCurrentFrame.N; io++)if(mCurrentFrame.mvbOutlier[io])mCurrentFrame.mvpMapPoints[io]=NULL;}//如果还是不能够满足就放弃了}

(8)如果还行,只能放弃

相关文章:

nodejs 中间件 反向代理 接口转发

背景 随着后端业务系统的增加&#xff0c;纵向需求不断扩展&#xff0c;一个业务系统已经无法满足需求了&#xff0c;衍生出多个业务系统&#xff0c;对外暴露的ip、端口就可能有多个&#xff0c;此时不方便外部接口调用&#xff0c;有些特殊行业客户出于安全性考虑不发提供多…

oneinstack

https://oneinstack.com/转载于:https://www.cnblogs.com/diyunpeng/p/9740895.html

最近在做托盘时,发现 CnTrayIcon1的OnClick 事件,不能被其它按钮来执行,蛋疼。...

比如&#xff1a; procedure TForm1.Button1Click(Sender: TObject);begin CnTrayIcon1.OnClick ; // 这句就是不能通过&#xff01;&#xff01;end; 有过路的高手&#xff0c;指点学生一下。谢谢转载于:https://www.cnblogs.com/hahy8008/p/6783614.html

Linux02-帮助手册

目录 一、man手册 1.1 man的基本使用 1.2 mandb更新文档 二、/usr/share/doc 三、access.redhat.com 门户 一、man手册 1.1 man的基本使用 man就是mannual的缩写&#xff0c;手册的意思。Linux的命令很多&#xff0c;参数选项更多&#xff0c;人脑一般是记不住的&…

ORB_SLAM2中Tracking线程

Tracking线程是ORB_SLAM2的主线程。在System.cc中&#xff0c;使用构造函数进行了初始化&#xff0c;开启了三个线程。 可执行程序—>System构造函数&#xff08;初始化三个线程&#xff09;—>处理输入的帧&#xff08;TrackMonocular&#xff09;—>调用Tracking线程…

selenium的基础知识点

from selenium import webdriver from scrapy.selector import Selector#模拟登陆 browser webdriver.Chrome(executable_pathChromedriver.exe) #路径是Chromedriver.exe的存放位置&#xff0c;windows下只要配置好这个环境就不需要了browser.get(http://w) #需要登陆的那个网…

iOS 直播专题2-音视频采集

从设备(手机)的摄像头、MIC中采集音频、视频的原始数据ios的音视频采集可以从AVFoundation框架里采集 视频采集 这里我们选取GPUImage来采集视频,因为这个框架集成了很多视频滤镜,例如美颜 采集流程: 摄像头采集视频代码 GPUImageVideoCamera.m // 从前摄像头或后摄像头…

bzoj 4871: [Shoi2017]摧毁“树状图”

4871: [Shoi2017]摧毁“树状图” Time Limit: 25 Sec Memory Limit: 512 MBSubmit: 53 Solved: 9[Submit][Status][Discuss]Description 自从上次神刀手帮助蚯蚓国增添了上千万人口&#xff08;蚯口&#xff1f;&#xff09;&#xff0c;蚯蚓国发展得越来越繁荣了&#xff01…

Linux03-本地账户和组

目录 一、本地账户/etc/passwd 二、本地组/etc/group 三、切换账户su - 四、增删改本地账户useradd、userdel、usermod 五、账户默认配置文件/etc/login.defs 六、设置密码passwd(5)命令 七、增删改组groupadd、groupdel和groupmod 八、通过sudo以root身份运行命令 九…

ORB_SLAM2单目初始化策略

基本流程 单目初始化程序存储在Initializer.cc中   需要注意&#xff0c;对于双目/RGB-D相机&#xff0c;初始化时&#xff0c;由于可以直接获得相机的深度信息&#xff0c;因此无需求H/F&#xff0c;直接作为关键帧插入就行。   使用RANSACDLT求解H&#xff0c;RANSAC八点…

Powerdesigner逆向工程64位Oracle数据库

Powerdesigner老版本不支持64位Client&#xff0c;新版本弄不到破解码 解决方法&#xff0c;用Powerdesigner32位Oracle Clent访问64位Oracle Server 遇到的坑分享下 安装完64位的Oracle Server ,32位的 Oracle Clent默认的listener.ora文件有PROGRAM和ENVS这两个节点 Plsql(3…

运行jsp时,报错404

The origin server did not find a current reprsentation for the target resource or is not willing to disclose that one exists. 解决&#xff1a; 1. web.xml文件位置是否放错&#xff0c;应该放在WebContent/WEB-INF文件夹中 2. web.xml文件中是否有拼写错误&#xff0…

iOS 直播专题3-前置处理

前置处理 对视频添加美颜、水印、滤镜等对音频进行混音、消除环境音、声音特效等上一篇iOS 直播专题2-音视频采集提到视频采集采用的是GPUImage框架,这个框架集成了很多滤镜效果 这里主要介绍美颜、水印处理 处理流程: 美颜 这里的美颜效果用的是GPUImageBeautyFilter 功…

ORA-10873解决办法

今天&#xff0c;发现SAP系统的oracle数据库宕掉了。报错ORA-10873&#xff0c;经过查证解决该问题。记录一下&#xff0c;备忘。 一、问题 Oracle版本为12.1.0.2.0&#xff0c;在启动服务器后启动数据库startup&#xff0c;报错ORA-10873。 二、查证 到SAP Support Portal上…

ORB_SLAM2局部建图线程

局部建图线程入口&#xff1a;可执行程序在初始化三个线程的时候&#xff0c;在System.cc的构造函数中进入局部建图线程 mpLocalMapper new LocalMapping(mpMap, //指定使iomanipmSensorMONOCULAR); // TODO 为什么这个要设置成为MONOCULAR&#xff1f;&#xff1f;&#…

十一连测day1

这次测试&#xff0c;是福建第三中学的某同学出的&#xff0c;感觉难度还行吧&#xff0c;今天我就浅谈一下这场比赛的时间分配与心得 打开题目&#xff0c;看到了T1&#xff0c;这题是一道计数题吧&#xff0c;感觉心态一下子就崩了&#xff0c;100%的数据点应该是组合数学容斥…

iOS 直播专题5-推流

常用的推流协议有: 协议内容RTP实时流传输协议,但不保证服务质量RTCPRTP数据流协议的一个姐妹协议,为RTP提供服务质量反馈SRTP & SRTCPRTP和RTCP的安全版本,提供数据加密、消息认证功能RTSP控制声音或影像的多媒体数据串流协议RTMPADOBE公司播放器与服务器之间多媒体数…

centos6.5-vsftp搭建

我的机子是默认是没有的vsftp。 yum install -y vsftp 创建账户专为ftp而生。useradd ftp01 更改账户不可登录系统。usermod -s /sbin/nologin ftp01 vsftp默认是可以匿名登录的&#xff0c;也是默认的端口&#xff0c;这些不安全选项都要修改&#xff01; anonymous_enableYES…

Linux04-文件系统权限与ACL权限

目录 一、文件系统权限 1.1、认识文件系统权限 1.2、管理文件系统权限 1.3、特殊权限 1.4、默认权限 二、ACL权限 2.1、ACL本质是文件系统的一个挂载选项 2.2、更改文件的ACL权限 2.3、设置文件和目录的默认ACL权限 Linux中的权限管理分为两种类型 用户自主访问控制&…

ORB_SLAM2帧Frame

在追踪线程的一开始就会创建一个帧 cv::Mat Tracking::GrabImageMonocular(const cv::Mat &im,const double &timestamp)构造函数 在构造函数中&#xff0c;会对特征点进行提取。 ExtractORB(0,imGray);特征点分配至网格 将图像划分为48*64的网格&#xff0c;然后将…

Servlet的基本架构

Servlet的基本架构&#xff1a; package test;import java.io.IOException;import javax.servlet.ServletException;import javax.servlet.http.HttpServlet;import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; public class Serv…

ORACLE 用户权限管理

Oracle创建用户的语法&#xff1a; CREATE USER username IDENTIFIED BY password OR IDENTIFIED EXETERNALLY OR IDENTIFIED GLOBALLY AS CNuser [DEFAULT TABLESPACE tablespace] [TEMPORARY TABLESPACE temptablespace] [QUOTA [integer K[M] ] [UNLIMITED] ] ON tables…

iOS 直播专题6-流媒体服务器

常用的流媒体服务器有: nginx、SRS、BMS 这里主要介绍nginx、SRS 这里都用docker来运行流媒体服务器 docker 安装 下载Mac版docker stable 直接安装 注册一个docer账号直接登录SRS 安装 SRS guthub地址:https://github.com/ossrs/srs/ 启动上面安装的docker软件后,打开终端…

Linux05-进程管理

目录 一、进程 1.1、进程ID 1.2、列出进程 1.3、进程前后台 二、使用信号控制进程 三、以管理员身份注销用户&#xff08;踢掉在线用户&#xff09; 四、监控进程活动 4.1、负载平均值 4.2、实时进程监控 进程是已启动的可执行程序的运行中的实力。它由以下部分组成&a…

Mat常用赋值方式

参考https://blog.csdn.net/wanggao_1990/article/details/53264753 #include <iostream> #include <opencv2/opencv.hpp> #include <unordered_map> using namespace std; using namespace cv; int main(int argc,char** argv) {// 1Mat mat (Mat_<flo…

java modbus协议

概念 Modbus是一种串行通信协议&#xff0c;Modbus协议目前存在用于串口、以太网以及其他支持互联网协议的网络的版本。 大多数Modbus设备通信通过串口EIA-485物理层进行。 通讯格式 地址域功能码数据CRC校验(低字节在前)1字节1字节N字节2字节 在单片机硬件通讯串口行业&…

layui栅格布局问题

在使用layer.open弹出到窗口中&#xff0c;使用布局一直不起作用。 开始到写法如下, 目的是一行分成左右两块&#xff0c;比例为8:4等分。 <div class"layui-fluid"><div class"layui-row layui-col-space10"><div class"layui-col-md…

Unity3d载入外部图片文件

unity里的图片在生成时会压缩成资源文件&#xff0c;有时客户想自己放一些图片用unity显示&#xff0c;就必须载入外部图片。 大体思路&#xff1a;用Application.streamingAssetsPath或Application.dataPath来指定存放图片的相对路径。用DirectoryInfo获得目录。遍历后FileInf…

Linux06-服务、守护进程和systemd

目录 一、简介systemd 二、使用systemd 2.1、systemctl命令与systemd单元 2.2、控制系统服务 一、简介systemd RHEL6及以前&#xff0c;系统启动和服务器进程是由第一个进程 init 管理&#xff0c;init按顺序启动、启动慢。 RHEL7以后系统启动和服务器进程由 systemd系统和…

ORB_SLAM2回环检测

词典是特征点的描述子的集合&#xff0c;属于同一类特征的特征点的描述子组成单词。 在局部建图线程中&#xff0c;处理完一个关键帧后&#xff0c;会将其放入回环检测线程     在使用关键帧数据库搜索候选关键帧组&#xff08;DetectLoopCandidates&#xff09;的时候&…