文章目录
- 前言
- 一、OpenCV 中的物体跟踪算法
- 1、均值漂移(Mean Shift):
- 2、CamShift:
- 3、KCF(Kernelized Correlation Filters):
- 4、MIL(Multiple Instance Learning):
- 二、物体跟踪方法
- 1、基于特征的跟踪方法
- (1)光流法:
- (2)特征点跟踪法:
- 2、基于模型的跟踪方法
- 3、基于外观模型的跟踪方法
- 4、基于深度学习的跟踪方法
- 5、基于检测的跟踪方法
- 物体跟踪的一般步骤
- 三、常见的物体跟踪器介绍
- 四、调用摄像头物体跟踪
- 1、分步讲解
- (1)导库并创建
- (2)读取摄像头对象或者读取视频
- (3)循环读取视频的每一帧
- (4)当按下键盘中的S键时,开始追踪
- cv2.selectROI() 函数
- tracker.init(frame, roi)
- (5)当Tracking为True时条件满足,更新位置,绘制被追踪物体的外接矩形
- (6)这里表示摄像头显示每一毫秒读取一帧画面,当按下ESC键时跳出循环,停止读取,并释放摄像头资源,摧毁窗口,减少内存的占用。
- 完整代码
- 五、应用
- 视频监控领域
- 智能交通领域
- 体育领域
- 虚拟现实和增强现实领域
- 医学领域
前言
物体跟踪是在视频序列或图像流中持续监测和定位特定物体的过程。通过分析相邻帧之间物体的特征和位置变化,实现对物体运动的跟踪。
一、OpenCV 中的物体跟踪算法
1、均值漂移(Mean Shift):
基于概率分布的跟踪算法。它通过计算目标区域的颜色直方图,在后续帧中搜索与该直方图最匹配的区域,从而实现目标跟踪。该算法计算速度快,但对目标的尺度变化和旋转不鲁棒。
2、CamShift:
是均值漂移算法的扩展。它不仅能跟踪目标的位置,还能根据目标的大小和形状自适应地调整搜索窗口的大小和方向,对目标的尺度变化有一定的适应性。
3、KCF(Kernelized Correlation Filters):
基于相关滤波的跟踪算法。它利用核函数将目标特征映射到高维空间,通过学习目标的外观模型,在后续帧中快速定位目标。KCF 算法具有较高的跟踪精度和速度,对光照变化和部分遮挡有较好的鲁棒性。
4、MIL(Multiple Instance Learning):
采用多示例学习的方法来训练目标模型。它将目标区域划分为多个子区域,通过学习这些子区域的特征来跟踪目标。MIL 算法对遮挡和背景干扰具有较好的鲁棒性,但计算复杂度较高,跟踪速度相对较慢。
二、物体跟踪方法
1、基于特征的跟踪方法
(1)光流法:
光流是指图像中物体表面上的点在图像平面上的运动速度。通过计算相邻帧之间像素点的光流场,可以得到物体的运动信息,进而实现物体跟踪。该方法对物体的运动较为敏感,但对光照变化和噪声的鲁棒性相对较差。
(2)特征点跟踪法:
首先在图像中提取一些具有独特性和稳定性的特征点,如 SIFT、SURF、ORB 等特征点。然后在后续帧中通过匹配这些特征点来跟踪物体的运动。这种方法对物体的旋转、尺度变化和光照变化有一定的适应性,但当特征点被遮挡或丢失时,可能会影响跟踪效果。
2、基于模型的跟踪方法
模板匹配法:在第一帧中手动或自动选择一个目标模板,然后在后续帧中通过搜索与模板最相似的区域来定位目标。常用的相似性度量方法有归一化互相关(NCC)等。该方法简单直观,但对目标的尺度变化、旋转和光照变化的适应性较差,且计算量较大。
3、基于外观模型的跟踪方法
通过学习目标物体的外观模型来进行跟踪。例如,使用主成分分析(PCA)等方法对目标的图像特征进行降维,建立目标的外观模型。在跟踪过程中,根据当前帧的图像特征与外观模型的匹配程度来确定目标的位置。这种方法对目标的外观变化有一定的适应性,但需要大量的训练数据来建立准确的外观模型。
4、基于深度学习的跟踪方法
孪生网络:孪生网络是一种基于深度学习的物体跟踪方法,它通过孪生结构的神经网络学习目标与搜索区域之间的相似性度量。在训练过程中,孪生网络通过大量的图像对来学习如何区分目标物体和背景,从而能够在新的视频序列中快速准确地定位目标。孪生网络具有较高的跟踪精度和速度,对各种复杂场景和目标变化具有较好的鲁棒性。
5、基于检测的跟踪方法
利用深度学习目标检测算法,如 Faster R-CNN、YOLO 等,在每一帧中对目标进行检测,然后通过数据关联算法将不同帧中的检测结果进行关联,实现物体跟踪。这种方法能够利用深度学习强大的特征提取能力,对目标的检测和跟踪效果较好,但计算量较大,实时性相对较差。
物体跟踪的一般步骤
目标初始化:在第一帧图像中指定要跟踪的目标物体,可以通过手动选择目标区域或使用目标检测算法来确定目标的初始位置和大小。
特征提取:根据选择的跟踪算法,提取目标物体的特征,如颜色、纹理、形状等。这些特征将用于在后续帧中识别和定位目标。
跟踪过程:在后续的视频帧中,根据上一帧的跟踪结果,利用选定的跟踪算法在当前帧中搜索目标物体的新位置。算法会根据目标的特征和运动模型,预测目标可能出现的位置,并在该区域内进行匹配和定位。
结果更新:将当前帧中目标的位置和状态信息更新到跟踪器中,以便为下一帧的跟踪提供初始条件。同时,根据需要可以对目标的特征模型进行在线学习和更新,以适应目标外观的变化。
三、常见的物体跟踪器介绍
1、BOOSTING 跟踪器
原理:基于 AdaBoost 算法,通过迭代训练多个弱分类器并组合成强分类器。在跟踪过程中,不断利用样本更新分类器,以区分目标和背景。
特点:
精度较低,在目标外观变化、光照变化或存在遮挡时,容易丢失目标。
计算速度较慢,实时性较差。
对目标外观变化的适应性较弱。
适用场景:适用于目标外观相对稳定、光照变化小且对精度要求不高的简单场景。
import cv2
boosting_tracker = cv2.legacy.TrackerBoosting_create()
2、MIL(Multiple Instance Learning)跟踪器
原理:采用多示例学习方法,将目标区域划分为多个子区域(示例),通过学习这些子区域的特征来训练目标模型。在跟踪时,根据模型匹配目标位置。
特点:
对部分遮挡有一定的鲁棒性,能够在目标被部分遮挡时继续跟踪。
跟踪精度一般,当目标快速运动或外观变化剧烈时,跟踪效果不佳。
计算复杂度较高,速度较慢。
适用场景:适用于目标可能会被部分遮挡,但运动速度相对较慢、外观变化不太剧烈的场景。
import cv2
mil_tracker = cv2.legacy.TrackerMIL_create()
3、 KCF(Kernelized Correlation Filters)跟踪器
原理:基于相关滤波的方法,通过核函数将目标特征映射到高维空间,学习目标的外观模型,在后续帧中利用相关滤波快速定位目标。
特点:
跟踪速度快,具有较好的实时性。
对目标的尺度变化和部分遮挡有一定的适应性。
精度相对较高,但在目标外观发生较大变化时,跟踪效果会受到影响。
适用场景:适用于对实时性要求较高,目标外观变化不大、运动速度适中的场景。
import cv2
kcf_tracker = cv2.TrackerKCF_create()
4、CSRT(Discriminative Correlation Filter with Channel and Spatial Reliability)跟踪器
原理:同样基于相关滤波,通过引入通道和空间可靠性信息,提高目标跟踪的精度和鲁棒性。
特点:
跟踪精度高,在目标外观变化、尺度变化和遮挡等情况下,都能保持较好的跟踪效果。
计算速度相对较慢,实时性不如 KCF 跟踪器。
适用场景:适用于对跟踪精度要求较高,目标外观和尺度可能会发生变化,且存在一定遮挡的复杂场景。
import cv2
csrt_tracker = cv2.legacy.TrackerCSRT_create()
5、MEDIANFLOW 跟踪器
原理:基于光流法,通过计算目标区域内像素点的光流,预测目标在后续帧中的位置。使用中值流的方法来提高跟踪的稳定性。
特点:
跟踪速度快,能够实时处理视频流。
对目标的运动速度和方向变化较为敏感,在目标运动平稳时,跟踪效果较好。
对遮挡和外观变化的鲁棒性较差,容易丢失目标。
适用场景:适用于目标运动平稳、无明显遮挡和外观变化的场景,如监控视频中的静态场景跟踪。
import cv2
medianflow_tracker = cv2.legacy.TrackerMedianFlow_create()
6、TLD(Tracking - Learning - Detection)跟踪器
原理:结合了跟踪(Tracking)、学习(Learning)和检测(Detection)三个模块。跟踪模块负责在当前帧中预测目标的位置;学习模块不断更新目标的外观模型;检测模块用于在整个图像中搜索目标,以应对目标丢失或遮挡的情况。
特点:
对目标的长期跟踪效果较好,能够在目标长时间消失后重新检测到目标。
容易产生漂移问题,即跟踪结果逐渐偏离真实目标。
计算量较大,实时性较差。
适用场景:适用于需要对目标进行长时间跟踪,且目标可能会暂时消失或被遮挡的场景。
import cv2
tld_tracker = cv2.legacy.TrackerTLD_create()
四、调用摄像头物体跟踪
1、分步讲解
(1)导库并创建
import cv2
tracker=cv2.TrackerCSRT_create() #创建CRST跟踪器
tracking=False #tracking 一般用来表示是否处于跟踪状态。False 意味着当前并未开始跟踪目标。
(2)读取摄像头对象或者读取视频
cap=cv2.VideoCapture(0)
写零表示调用电脑自身的摄像头,里面还可以传视频文件(传入参数为视频的保存路径)
(3)循环读取视频的每一帧
while True:
ret,frame=cap.read()
#使用read读取,视频或摄像头中的每一帧,ret表示视频是否读取成功,frame是指每一帧图像画面。
if not ret: #表示视频读取失败,则跳出循环
break
(4)当按下键盘中的S键时,开始追踪
if cv2.waitKey(1)==ord('s'):
tracking=True
roi=cv2.selectROI('Tracking',frame,showCrosshair=False)
tracker.init(frame,roi)
cv2.selectROI() 函数
其作用是让用户手动选取视频帧里的一个感兴趣区域(Region of Interest,简称 ROI)。
1、 ‘Tracking’:这是弹出的选择窗口的标题,当运行代码时,会出现一个名为 Tracking 的窗口,用户可以在这个窗口里进行 ROI 的选择操作。
2、frame:这是当前要处理的视频帧,也就是用户选择 ROI 所基于的图像。
3、showCrosshair=False:这个参数控制在选择 ROI 时是否显示十字线。设置为 False 表示不显示十字线;若设置为 True,在选择 ROI 的过程中会显示十字线,方便用户更精准地定位 ROI 的中心位置。
4、cv2.selectROI() 函数在用户完成 ROI 选择后,会返回一个包含 ROI 位置和大小信息的元组 (x, y, w, h),其中:
x 和 y 是 ROI 左上角的坐标。
w 和 h 分别是 ROI 的宽度和高度。
tracker.init(frame, roi)
调用了跟踪器对象 tracker 的 init() 方法,其作用是使用用户选择的 ROI 来初始化跟踪器。
1、frame:这是当前的视频帧,也就是用户选择 ROI 所在的那一帧图像。跟踪器会以这一帧为基准,对后续视频帧里的目标进行跟踪。
2、roi:这是前面通过 cv2.selectROI() 函数得到的 ROI 信息,跟踪器会根据这个 ROI 来确定要跟踪的目标。
(5)当Tracking为True时条件满足,更新位置,绘制被追踪物体的外接矩形
if tracking:
success,box=tracker.update(frame)
if success:
x,y,w,h=[int(v) for v in box]
cv2.rectangle(frame,(x,y),(x+w,y+h),(0,255,0),2)
cv2.imshow('Tracking',frame)
success, box = tracker.update(frame)
调用了跟踪器对象 tracker 的 update() 方法,用于在当前视频帧 frame 中更新目标的位置。
返回值:
1、success:一个布尔值,用于表示目标跟踪是否成功。如果成功跟踪到目标,success 为 True;否则为 False。
2、 box:一个包含目标位置和大小信息的元组,通常格式为 (x, y, w, h),其中 x 和 y 是目标矩形框左上角的坐标,w 和 h 分别是矩形框的宽度和高度。
(6)这里表示摄像头显示每一毫秒读取一帧画面,当按下ESC键时跳出循环,停止读取,并释放摄像头资源,摧毁窗口,减少内存的占用。
if cv2.waitKey(1)==27:
break
cap.release()
cv2.destroyAllWindows()
完整代码
import cv2
tracker=cv2.TrackerCSRT_create()
tracking=False
cap=cv2.VideoCapture(0) #写零表示调用电脑自身的摄像头,里面还可以传视频文件(传入参数为视频的保存路径)
while True:
ret,frame=cap.read()
if not ret:
break
if cv2.waitKey(1)==ord('s'):
tracking=True
roi=cv2.selectROI('Tracking',frame,showCrosshair=False)
tracker.init(frame,roi)
if tracking:
success,box=tracker.update(frame)
if success:
x,y,w,h=[int(v) for v in box]
cv2.rectangle(frame,(x,y),(x+w,y+h),(0,255,0),2)
cv2.imshow('Tracking',frame)
if cv2.waitKey(1)==27:
break
cap.release()
cv2.destroyAllWindows()
五、应用
物体跟踪在多个领域都有广泛的应用
视频监控领域
行为分析:通过对监控视频中人物或物体的跟踪,分析其行为模式,如是否有异常徘徊、奔跑等行为,可用于公共场所的安全监控,及时发现潜在的安全威胁。
事件检测:检测特定事件的发生,如检测商场中的顾客摔倒、打架等行为,以便及时采取相应措施。
智能交通领域
车辆跟踪与流量监测:在交通路口或高速公路上,对车辆进行跟踪,获取车辆的行驶速度、轨迹等信息,从而实现交通流量的统计和分析,为交通管理部门提供决策依据,优化交通信号灯时长和道路规划。
辅助自动驾驶:在自动驾驶车辆中,物体跟踪技术可以实时跟踪周围的车辆、行人、交通标志等物体,为车辆的决策和控制提供重要信息,帮助车辆避免碰撞、规划行驶路径等。
体育领域
运动员表现分析:在体育比赛中,通过跟踪运动员的运动轨迹和动作,可以对运动员的表现进行分析,帮助教练和运动员了解技术动作的优缺点,制定训练计划,提高运动成绩。
比赛转播:在体育赛事转播中,物体跟踪技术可以实时跟踪运动员和球的位置,为观众提供更丰富的比赛信息,如球员的跑动距离、速度、传球路线等,增强比赛的观赏性和专业性。
虚拟现实和增强现实领域
交互体验:在虚拟现实和增强现实应用中,通过跟踪用户的头部、手部等身体部位的运动,实现与虚拟环境的自然交互。例如,用户可以通过头部转动来观察虚拟场景,通过手部动作来操作虚拟物体。
场景重建:物体跟踪技术可以帮助重建真实场景的三维模型,将虚拟元素与真实场景更好地融合,提高增强现实应用的沉浸感。
医学领域
手术导航:在手术过程中,通过跟踪手术器械和患者体内的器官、组织等,为医生提供实时的位置信息,辅助医生进行精确的手术操作,提高手术的安全性和准确性。
康复治疗:在康复治疗中,跟踪患者的肢体运动,评估康复训练的效果,为康复治疗方案的调整提供依据。