KCF追踪器在opencv和RM中的应用

2023-10-27

1.理论部分

【参考文档】KCF目标跟踪方法分析与总结

概念

(1)判别式模型和生成式模型
  • 判别式模型

根据训练数据得到分类函数和分界面,比如说根据SVM模型得到一个分界面,然后直接计算条件概率 P(y|x),我们将最大的 P(y|x)。

  • 生成式模型

首先根据猫的特征学习出一个猫的模型,再根据狗的特征学习出狗的模型,之后分别计算新样本X跟三个类别的联合概率 P(y|x),然后根据贝叶斯公式,分别计算 P(y|x),选择三类中最大的 P(y|x)作为样本的分类

2.实战

2.1.在opencv中

2.1.1跟踪器结构

在这里插入图片描述
基本上所有的追踪方法都会继承cv::track,在使用的时候也是使用向上转型的技术(即创建父类类型的变量指向子类对象
同时track类包含三个基本函数
①析构函数
②初始化函数init(虚函数)
③更新函数update(虚函数)
init和update都是虚函数,在相应的追踪器中实现

2.1.2. init

使用目标周围的已知边界框初始化跟踪器
在这里插入图片描述
参数
image 初始帧
boundingBox 初始边界框

2.1.2 update()

更新跟踪器,找到目标的新的最可能的边界框(返回到boundingBox中)
请添加图片描述
参数:

  • image 当前帧
  • boundingBox 表示新目标位置的边界框(如果返回为 true,则未以其他方式修改)

返回值:
True 表示目标已定位,false 表示跟踪器无法在当前帧中找到目标。请注意,后者并不意味着跟踪器已经失败,也许目标确实从框架中丢失(例如,看不见)

2.2 使用

【参考文档】opencv自带kcf算法实现目标跟踪

  1. 创建kcf追踪器
Ptr<Tracker> tracker = TrackerKCF::create()
  1. 选择目标roi(boundingbox)
    这里是使用selectROI这个函数
    在这里插入图片描述
  • 功能:允许用户在给定图像上选择 ROI。

该功能创建一个窗口,并允许用户使用鼠标选择ROI。控件:使用或完成选择,使用键取消选择(函数将返回零 cv::Rect)

  • 参数:
    (1)windowName 窗口名
    (2)img 用于选择roi的图像
    (3)showCrosshair 果将显示选择矩形的真十字准线。
    (4)fromCenter如果真正的选择中心将与初始鼠标位置匹配。相反情况下,选择矩形的一角将对应于初始鼠标位置。
  1. 初始化追踪器 tracker->init(frame, roi)
  2. 对每一帧进行追踪tracker->update(frame, roi)

2.2.1 完整代码

#include <opencv2/core/utility.hpp>
#include <opencv2/tracking.hpp>
#include <opencv2/videoio.hpp>
#include <opencv2/highgui.hpp>
#include <iostream>
#include <cstring>

using namespace std;
using namespace cv;

int main() {
    // declares all required variables
    //! [vars]
    Rect2d roi;
    Mat frame;
    //! [vars]

    // create a tracker object
    //Ptr<Tracker> tracker = Tracker::create("KCF");
    Ptr<Tracker> tracker = TrackerKCF::create();
    //! [create]

    // set input video
    //! [setvideo]
    std::string video = "E:\\car.mp4";
    VideoCapture cap(video);
    //! [setvideo]

    // get bounding box
    //! [getframe]
    cap >> frame;
    //! [getframe]
    //! [selectroi]选择目标roi以GUI的形式
    roi = selectROI("tracker", frame);
    //! [selectroi]

    //quit if ROI was not selected
    if (roi.width == 0 || roi.height == 0)
        return 0;

    // initialize the tracker
    //! [init]
    tracker->init(frame, roi);
    //! [init]

    // perform the tracking process
    printf("Start the tracking process\n");
    for (;; ) {
        // get frame from the video
        cap >> frame;

        // stop the program if no more images
        if (frame.rows == 0 || frame.cols == 0)
            break;

        // update the tracking result
        //! [update]
        tracker->update(frame, roi);
        //! [update]

        //! [visualization]
        // draw the tracked object
        rectangle(frame, roi, Scalar(255, 0, 0), 2, 1);

        // show image with the tracked object
        imshow("tracker", frame);
        //! [visualization]
        //quit on ESC button
        if (waitKey(1) == 27)
            break;
    }

    return 0;
}

3 在RM中的使用

以桂电的开源代码为例

3.1 跟踪器初始化armorTrackerInit

整体的逻辑:
请添加图片描述

3.1.1跟踪失败

        //追踪失败
        src(_trackerRect).copyTo(img);
        if (!_tracker->update(_src, _trackerRect)) {
            _trackerSuccess = false; 
            _searchRect.x = _trackerRect.x - _trackerRect.width;
            _searchRect.y = _trackerRect.y - _trackerRect.height;
            _searchRect.height = _trackerRect.height * 3;
            _searchRect.width = _trackerRect.width * 3;
            _searchRect &= cv::Rect2d(0, 0, _imgWidth, _imgHeight);
        }

_searchRect &= cv::Rect2d(0, 0, _imgWidth, _imgHeight)限制面积不越界
请添加图片描述

其他代码都挺简单的,就不细说了,下面给出完整片段

3.1.2 调用关系

在识别过程函数process中被调用

//识别过程函数
cv::RotatedRect ArmorDistinguish::process(const cv::Mat& src, EnemyColor enemyColor, CarType carType, bool isReset, DistinguishMode distinguishMode, float yawAngle, bool topRest) {
#ifdef USE_KCF
    armorTrackerInit(src, enemyColor);
#else
    imagePreprocess(src, enemyColor);
#endif

3.1.3 完整代码

#ifdef USE_KCF
//kcf追踪器
void ArmorDistinguish::armorTrackerInit(const cv::Mat& src, EnemyColor enemyColor) {
    cv::Mat img;
    _size = src.size();
    _para.enemyColor = enemyColor;
    _params.detect_thresh = 0.03f;
    if (_isTrackerStart) {
        //追踪失败
        src(_trackerRect).copyTo(img);
        if (!_tracker->update(_src, _trackerRect)) {
            _trackerSuccess = false; 
            _searchRect.x = _trackerRect.x - _trackerRect.width;
            _searchRect.y = _trackerRect.y - _trackerRect.height;
            _searchRect.height = _trackerRect.height * 3;
            _searchRect.width = _trackerRect.width * 3;
            _searchRect &= cv::Rect2d(0, 0, _imgWidth, _imgHeight);
        }
        else {//_tracker->update(_src, _trackerRect)==True
            //越界则需要从全图搜索
            if ((_trackerRect & cv::Rect2d(0, 0, _imgWidth, _imgHeight)) != _trackerRect) {
                _searchRect = cv::Rect2d(0, 0, _imgWidth, _imgHeight);
            }
            //搜索区域需要扩大两倍
            else {
                _trackerSuccess = true;
                _searchRect.x = _trackerRect.x - _trackerRect.width / 2;
                _searchRect.y = _trackerRect.y - _trackerRect.height / 2;
                _searchRect.height = _trackerRect.height * 2;
                _searchRect.width = _trackerRect.width * 2;
                _searchRect &= cv::Rect2d(0, 0, _imgWidth, _imgHeight);
            }//else
        }//else
        src(_searchRect).copyTo(_src);
        imshow("img", img);
    }
    else {//_isTrackerStart==False
        _trackerSuccess = false;
        _searchRect = cv::Rect2d(0, 0, _imgWidth, _imgHeight);
        _src = src;
    }

    imshow("_src", _src);
    cv::waitKey(1);
}
#endif

3.2 识别过程函数process

仅包含kcf部分

3.2.1

3.2.2 包含kfc的代码

完整代码见https://github.com/freezing00/Baldr/blob/main/Src/armor/armorDistinguish.cpp

//识别过程函数
cv::RotatedRect ArmorDistinguish::process(const cv::Mat& src, EnemyColor enemyColor, CarType carType, bool isReset, DistinguishMode distinguishMode, float yawAngle, bool topRest) {

#ifdef USE_KCF
    armorTrackerInit(src, enemyColor);
#else//正常图像的预处理
    imagePreprocess(src, enemyColor);
#endif
    //从轮廓中找出类似灯条矩形
    
    //类似灯条矩形过滤器

    //选择一个最优目标

    if (_resultRect.size.width > 0) {
        //中间点的坐标再加上restoreRect的坐标
#ifdef USE_KCF
        _isReulstFind = true;
        _isTrackerStart = true;
        if (_isReulstFind) {
            float lightBarWidthL = _leftLightBar.size.width < _leftLightBar.size.height ? _leftLightBar.size.width : _leftLightBar.size.height;
            float lightBarHeightL = _leftLightBar.size.width > _leftLightBar.size.height ? _leftLightBar.size.width : _leftLightBar.size.height;
            float lightBarWidthR = _rightLightBar.size.width < _rightLightBar.size.height ? _rightLightBar.size.width : _rightLightBar.size.height;
            float lightBarHeightR = _rightLightBar.size.width > _rightLightBar.size.height ? _rightLightBar.size.width : _rightLightBar.size.height;

            cv::Point2d recttl = cv::Point2d((double)(_leftLightBar.center.x - 2.0 * lightBarWidthL), (double)(_leftLightBar.center.y - 1.5 * lightBarHeightL));
            cv::Point2d rectbr = cv::Point2d((double)(_rightLightBar.center.x + 2.0 * lightBarWidthR), (double)(_rightLightBar.center.y + 1.5 * lightBarHeightR));
            recttl += cv::Point2d(_searchRect.x, _searchRect.y);
            rectbr += cv::Point2d(_searchRect.x, _searchRect.y);
            _trackerRect = cv::Rect2d(recttl, rectbr);
            _trackerRect &= cv::Rect2d(0, 0, _imgWidth, _imgHeight);
            //---------------创建KCF追踪器-----------------------------------------------
            _tracker = cv::TrackerKCF::create();
            _tracker->init(_src, _trackerRect);
        }
        resultRect.center += cv::Point2f((float)_searchRect.x, (float)_searchRect.y);
#else
        _resultRect.center += cv::Point2f((float)_restoreRect.x, (float)_restoreRect.y);
#endif
        _resultRect.points(_vertices);
        //记录上一刻的检测区域
        _resLast = _resultRect;
        _lost_cnt = 0;
        //记录上一刻的时间
        _lastTime = (double)(cv::getTickCount());

    }
    else {
#ifdef USE_KCF
        _isTrackerStart = false;
        _isReulstFind = false;
        return cv::RotatedRect();

#endif //USE_KCF
    }

}

3.3 小结

在装甲板识别中使用KFC的整体逻辑
请添加图片描述

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

KCF追踪器在opencv和RM中的应用 的相关文章

  • 在 QtCreator 中将 OpenCV 2.3 与 Qt 结合使用

    随着 OpenCV 2 3 版本终于发布 我想在我的系统上编译并安装这个最新版本 由于我经常使用 Qt 和 QtCreator 我当然希望能够在我的 Qt 项目中使用它 我已经尝试了几种方法几个小时 但总是出现错误 第一次尝试 使用WITH
  • 无法在 Windows 7 机器中使用 OpenCV 2.4.3、Python 2.7 打开“.mp4”视频文件

    我目前正在进行一个涉及读取 mp4 视频文件的项目 我遇到的问题是它在Windows 7机器上使用Python 2 7 32位 OpenCV 2 4 3 cv2 pyd 代码片段如下 try video cv2 VideoCapture v
  • opencv形态扩张滤波器作为最大滤波器

    就像中值滤波器的定义一样 我可以将 最大滤波器 定义为局部窗口 例如dst x y max 3x3 局部窗口像素 但我在opencv中找不到这样的过滤器 最接近的是 dilate 函数 然后我使用 dilate 函数的默认配置 但结果不正确
  • OpenCV 3 中的 FLANN 错误

    我运行的是 Ubuntu 14 04 我正在尝试使用 openCV 3 运行 FLANN 但出现错误 下面的所有内容都是通过使用 AKAZE 和 ORB 进行尝试的 但代码来自我尝试使用 ORB 的情况 我使用 ORB 来查找描述符和关键点
  • 如何将输出视频保存到 OpenCV 中的文件中

    我想将输出视频保存到文件中而不是显示它并尝试使用 cvcaptureimage 但仍然无法获得结果 include
  • opencv 2.3.* 读取不工作

    我无法让 imread 工作 与这个人有同样的问题 OpenCV imwrite 2 2 在 Windows 7 上导致异常 并显示消息 OpenCV 错误 未指定错误 无法找到指定扩展名的编写器 https stackoverflow c
  • OpenCV C++ 如何知道每行的轮廓数进行排序?

    我有一个二值图像 https i stack imgur com NRLVv jpg在这张图片中 我可以使用重载的函数轻松地对从上到下 从左到右找到的轮廓进行排序std sort 我首先通过以下方式从上到下排序 sort contours
  • 为什么我无法在 Mac 12.0.1 (Monterey) 上使用 pip 安装 OpenCV? [复制]

    这个问题在这里已经有答案了 当我尝试使用 python pip 安装 OpenCV 时 它显示了以下内容 Remainder of file ignored Requirement already satisfied pip in Libr
  • 使用 OpenCV 和/或 Numpy 对两个图像进行 Alpha 混合 [重复]

    这个问题在这里已经有答案了 我想将一个填充纯色的半透明矩形添加到已加载的半透明 PNG 中 这是我正在使用的输入图像示例 该图像加载了标准cv2 IMREAD UNCHANGED标志 以便完美保留 alpha 通道 该输入图像存储在imag
  • uri 警告中缺少端口:使用 Python OpenCV cv2.VideoCapture() 打开文件时出错

    当我尝试流式传输 ipcam 时 出现了如下所示的错误 tcp 000000000048c640 uri 中缺少端口 警告 打开文件时出错 build opencv modules videoio src cap ffmpeg impl h
  • OpenCV 跟踪器:模型未在函数 init 中初始化

    在视频的第一帧 我运行一个对象检测器 它返回对象的边界框 如下所示
  • 在 Python 中将 OpenCV 帧流式传输为 HTML

    我正在尝试从 opencv Pyt hon 中的 URL 读取视频 然后逐帧处理它 然后将其发送到 HTML 页面 But I am only getting the first frame after that the program g
  • 如何使用 colorchecker 在 opencv 中进行颜色校准?

    我有数码相机获取的色彩检查器图像 我如何使用它来使用 opencv 校准图像 按照以下颜色检查器图像操作 您是想问如何进行颜色校准或如何使用 OpenCV 进行校准 为了进行颜色校准 您可以使用校准板的最后一行 灰色调 以下是您应该逐步进行
  • 如何将 Mat (opencv) 转换为 INDArray (DL4J)?

    我希望任何人都可以帮助我解决这个任务 我正在处理一些图像分类并尝试将 OpenCv 3 2 0 和 DL4J 结合起来 我知道DL4J也包含Opencv 但我认为它没什么用 谁能帮我 如何转换成 INDArray 我尝试阅读一些问题here
  • 在 Visual Studio 2012 中安装 OpenCV

    我正在尝试安装 OpenCV 来与 Visual Studio 一起使用 我使用的是2012Pro版本 但我认为它应该与vs10相同 我正在关注这个教程 http docs opencv org doc tutorials introduc
  • 如何使用 opencv.omnidir 模块对鱼眼图像进行去扭曲

    我正在尝试使用全向模块 http docs opencv org trunk db dd2 namespacecv 1 1omnidir html用于对鱼眼图像进行扭曲处理Python 我正在尝试适应这一点C 教程 http docs op
  • OpenCv读/写视频色差

    我试图简单地使用 openCV 打开视频 处理帧并将处理后的帧写入新的视频文件 我的问题是 即使我根本不处理帧 只是打开视频 使用 VideoCapture 读取帧并使用 VideoWriter 将它们写入新文件 输出文件看起来比输入更 绿
  • 查找具有不同强度/亮度的相似图像

    假设我有如下图像 我可以选择什么来比较两个图像之间的相似度 显然它们是相同的图像 只是亮度不同 我找不到任何可行的方法 目前我最好的选择是训练 cnn 或自动编码器并比较输出的特征向量 但这似乎有点矫枉过正 任何提示将不胜感激 相当强大的工
  • 如何使用 AdaBoost 进行特征选择?

    我想使用 AdaBoost 从大量 100k 中选择一组好的特征 AdaBoost 的工作原理是迭代功能集并根据功能的执行情况添加功能 它选择对现有特征集错误分类的样本表现良好的特征 我目前正在 Open CV 中使用CvBoost 我得到
  • 如何加速 svm.predict?

    我正在编写一个滑动窗口来提取特征并将其输入到 CvSVM 的预测函数中 然而 我偶然发现 svm predict 函数相对较慢 基本上 窗口以固定的步幅长度在图像比例上滑动穿过图像 遍历图像加上提取每个图像特征的速度 窗口大约需要 1000

随机推荐

  • Ubuntu 16.04下deb包的安装及常用命令

    如果ubuntu要安装新软件 已有deb安装包 例如 iptux deb 但是无法登录到桌面环境 那该怎么安装 答案是 使用dpkg命令 dpkg命令常用格式如下 sudo dpkg I iptux deb 查看iptux deb软件包的详
  • 数据对象总结

    JavaScript对象 对象属于一种复合的数据类型 在对象中可以存储多个不同数据类型的属性 JavaScript 中的所有事物都是对象 字符串 数值 数组 函数 此外 JavaScript 还允许自定义对象 JavaScript 提供多个
  • C++函数调用那些事

    C 函数调用 C 形参带默认值的函数 带默认值的形参必须从右往左给 给出以下实例 int sum int x int y 无默认值函数 int sum int x int y 0 y有默认值 int sum int x 0 int y 0
  • c#初级

    类 创建一个类 public class A 访问修饰符 public公有 protected 受保护的 private私有的 public 在类内和类外都可以使用 public int a 定义一个字段a protected 他只能在类内
  • 模运算

    http blog csdn net ld326 article details 7880429 模运算即求余运算 模 是 Mod 的音译 模运算多应用于程序编写中 Mod的含义为求余 模运算在数论和程序设计中都有着广泛的应用 从奇偶数的判
  • 【Flutter造轮子】Text组件显示指定行文字,若有超出加...点击查看更多

    效果如上图 如果超出 显示 点击查看更多 正好凑够4行 再添加一个字便超出4行 原理 使用TextPainter逐渐添加字尝试 该组件超出的话 其属性didExceedMaxLines为true 代码如下 文字超出一定行 自动隐藏 并添加入
  • AI绘画指南:在CentOS7中训练Lora模型

    本次训练在centos7中完成 使用的训练脚本是 https github com Akegarasu lora scripts git https github com kohya ss sd scripts git 一 安装GPU环境
  • 【动态规划】合唱队形

    题目描述 n位同学站成一排 音乐老师要请其中的 n K 位同学出列 使得剩下的K位同学排成合唱队形 合唱队形是指这样的一种队形 设K位同学从左到右依次编号为1 2 K 他们的身高分别为T1 T2 TK 则他们的身高满足T1 lt Ti l
  • 关于代码家(干货集中营)共享android端知识点综合整理

    关于代码家 干货集中营 共享android端知识点综合整理 标签 开源项目自定义控件教程特效工具 2016 03 08 13 23 8520人阅读 评论 2 收藏 举报 分类 移动开发 28 版权声明 本文为博主原创文章 未经博主允许不得转
  • 探索MySQL错误: 1241 - Operand should contain 1 column(s)问题解决方案

    AI绘画关于SD MJ GPT SDXL百科全书 面试题分享点我直达 2023Python面试题 2023最新面试合集链接 2023大厂面试题PDF 面试题PDF版本 java python面试题 项目实战 AI文本 OCR识别最佳实践 A
  • Qt中moc问题(qt moc 处理 cpp)

    我用的是QT Designer 一般只有用到信号signals和槽slots时才会用到MOC 因为采用信号signals和槽slots是QT的特性 而C 没有 所以采用了MOC 元对象编译器 把信号signals和槽slots部分编译成C
  • 【华为OD统一考试B卷

    在线OJ 已购买本专栏用户 请私信博主开通账号 在线刷题 运行出现 Runtime Error 0Aborted 请忽略 华为OD统一考试A卷 B卷 新题库说明 2023年5月份 华为官方已经将的 2022 0223Q 1 2 3 4 统一
  • libevent源码学习(5):TAILQ_QUEUE解析

    目录 前言 结点定义 链表初始化 链表查询及遍历 链表查询 链表遍历 插入结点 头插法 尾插法 前插法 后插法 删除结点 替换结点 总结 前言 在libevent中使用到了TAILQ数据结构 看了一下其他资料 发现TAILQ这一数据结构不仅
  • TVM 0.9 在 ubuntu(任意版本)上的安装(简单且保姆级!)

    近一年来尝试过TVM在ubuntu16 04 ubuntu18 04 ubuntu20 04 以及windows上的安装 也看了官方教程和网上各种博客 踩坑无数 现在总结在Ubuntu上踩坑几率最小的安装流程如下 建议学习TVM一开始就在u
  • fisco-bcos使用caliper进行压力测试

    使用caliper对fisco bcos进行压力测试 通过Caliper进行压力测试程序 注意 官网给出的测试案例会出现错误 我会给出相应的解决方案 本文以centos系统为例进行测试 1 环境要求 第一步 配置基本环境 部署Caliper
  • 勇敢的人

    昨天刚写完做个勇敢的人 发现一篇博客写的非常好 于是果断给它转载一下 这位老师的发言 在某个瞬间打动了现在的我 请观看 https blog csdn net zkl99999 article details 46683535 关键字 毛尖
  • iOS检测网络连接状态

    请从Apple网站下载示例 点此下载 然后将Reachability h 和 Reachability m 加到自己的项目中 并引用 SystemConfiguration framework 就可以使用了 Reachability 中定义
  • Java 23种设计模式的分类和使用场景

    听说过GoF吧 GoF是设计模式的经典名著Design Patterns Elements of Reusable Object Oriented Software 中译本名为 设计模式 可复用面向对象软件的基础 的四位作者 他们分为是 E
  • Qt创建的子线程不断循环,主线程界面一直处于无响应状态

    说明 今天用子线程处理数据 但只创建了子线程 还没有来得及让子线程处理大量的数据 在子线程只作了简单处理 发现主线程界面一直不能响应 在主线程让子线程参数isStop true 也跳不出循环 while isStop emit mySign
  • KCF追踪器在opencv和RM中的应用

    1 理论部分 参考文档 KCF目标跟踪方法分析与总结 概念 1 判别式模型和生成式模型 判别式模型 根据训练数据得到分类函数和分界面 比如说根据SVM模型得到一个分界面 然后直接计算条件概率 P y x 我们将最大的 P y x 生成式模型