OpenCV-Python系列之稀疏光流

之前介绍的两种算法对于视频中的跟踪而言仍然有一定的局限性。这次我们来讨论一种光流估计的方法用于进行目标跟踪。

光流是物体或者摄像头的运动导致的两个连续帧之间的图像对象的视觉运动的模式。它是一个向量场,每个向量是一个位移矢量,显示了从第一帧到第二帧的点的移动,如图:

它显示了一个球在5个连续帧里的移动。箭头显示了它的位移矢量。光流在很多领域有应用:

·移动构建

·视频压缩

·视频稳定

光流在很多假设下有效:

1.物体像素强度在连续帧之间不变化

2.邻居像素有相似运动

考虑第一帧里的一个像素I(x,y,t)(检查新的维度,时间)。它在dt时间后的下一帧移动了(dx, dy)。所以因为那些像素都一样,强度也不变化。我们可以认为:

然后对右边做泰勒级数近似。除以dt得到下面的等式:

其中:

上面的等式被叫做光流等式,我们可以找到fx和fy,他们是图像梯度。类似的ft 是沿时间的梯度。但是(u, v)是未知的。我们无法解出这个等式。所以有一些方法来提供解决这个问题,其中一个是Lucas-Kanade。是由Bruce D. Lucas and Takeo Kanade两位作者提出来的,所以又被称为KLT。

KLT算法工作有三个假设前提条件:

·亮度恒定

·短距离移动

·空间一致性

Opencv中使用cv2.calcOpticalFlowPyrLK()函数计算一个稀疏特征集的光流,使用金字塔中的迭代 Lucas-Kanade 方法。来看函数原型:

nextPts,status,err = cv2.calcOpticalFlowPyrLK(prevImg, #上一帧图片

nextImg, #当前帧图片

prevPts, #上一帧找到的特征点向量

nextPts #与返回值中的nextPtrs相同

[, status[, err[, winSize

[, maxLevel[, criteria

[, flags[, minEigThreshold]]]]]]])

参数解释:

prevImg--> 上一帧图片;

nextImg--> 当前帧图片;

prevPts--> 上一帧找到的特征点向量;

nextPts--> 与返回值中的nextPtrs相同;

status--> 与返回的status相同;

err--> 与返回的err相同;

winSize--> 在计算局部连续运动的窗口尺寸(在图像金字塔中),default=Size(21, 21);

maxLevel--> 图像金字塔层数,0表示不使用金字塔, default=3;

criteria--> 寻找光流迭代终止的条件;

flags--> 有两个宏,表示两种计算方法,分别是OPTFLOW_USE_INITIAL_FLOW表示使用估计值作为寻找到的初始光流,OPTFLOW_LK_GET_MIN_EIGENVALS表示使用最小特征值作为误差测量,default=0;

minEigThreshold--> 该算法计算光流方程的2×2规范化矩阵的最小特征值,除以窗口中的像素数; 如果此值小于minEigThreshold,则会过滤掉相应的功能并且不会处理该光流,因此它允许删除坏点并获得性能提升, default=1e-4.

返回值:

nextPtrs--> 输出一个二维点的向量,这个向量可以是用来作为光流算法的输入特征点,也是光流算法在当前帧找到特征点的新位置(浮点数);

status--> 标志,在当前帧当中发现的特征点标志status==1,否则为0;

err--> 向量中的每个特征对应的错误率.

实现原理: 在第一帧图像中检测Shi-Tomasi角点,使用LK算法来迭代的跟踪这些特征点。迭代的方式就是不断向cv2.calcOpticalFlowPyrLK()中传入上一帧图片的特征点以及当前帧的图片。函数会返回当前帧的点,这些点带有状态1或者0,如果在当前帧找到了上一帧中的点,那么这个点的状态就是1,否则就是0。

实现流程:

·加载视频。

·调用cv2.GoodFeaturesToTrack 函数寻找兴趣点(关键点)。

·调用cv2.CalcOpticalFlowPyrLK 函数计算出两帧图像中兴趣点的移动情况。

·删除未移动的兴趣点。

·在两次移动的点之间绘制一条线段。

我们仍然使用之前的示例视频。

来看代码:import numpy as np

import cv2

cap = cv2.VideoCapture("test.avi")

# ShiTomasi 角点检测参数

feature_params = dict(maxCorners=100,

qualityLevel=0.3,

minDistance=7,

blockSize=7)

# lucas kanade光流法参数

lk_params = dict(winSize=(15, 15),

maxLevel=2,

criteria=(cv2.TERM_CRITERIA_EPS | cv2.TERM_CRITERIA_COUNT, 10, 0.03))

# 创建随机颜色

color = np.random.randint(0, 255, (100, 3))

# 获取第一帧,找到角点

ret, old_frame = cap.read()

# 找到原始灰度图

old_gray = cv2.cvtColor(old_frame, cv2.COLOR_BGR2GRAY)

# 获取图像中的角点,返回到p0中

p0 = cv2.goodFeaturesToTrack(old_gray, mask=None, **feature_params)

# 创建一个蒙版用来画轨迹

mask = np.zeros_like(old_frame)

while (1):

ret, frame = cap.read()

frame_gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)

# 计算光流

p1, st, err = cv2.calcOpticalFlowPyrLK(old_gray, frame_gray, p0, None, **lk_params)

# 选取好的跟踪点

good_new = p1[st == 1]

good_old = p0[st == 1]

# 画出轨迹

for i, (new, old) in enumerate(zip(good_new, good_old)):

a, b = new.ravel()

c, d = old.ravel()

mask = cv2.line(mask, (a, b), (c, d), color[i].tolist(), 2)

frame = cv2.circle(frame, (a, b), 5, color[i].tolist(), -1)

img = cv2.add(frame, mask)

cv2.imshow('frame', img)

k = cv2.waitKey(100) & 0xff

if k == 27:

break

# 更新上一帧的图像和追踪点

old_gray = frame_gray.copy()

p0 = good_new.reshape(-1, 1, 2)

cv2.destroyAllWindows()

cap.release()

结果示例:

稀疏光流python_【原创】OpenCV-Python系列之稀疏光流(五十九)相关推荐

  1. [Python从零到壹] 五十九.图像增强及运算篇之图像锐化Scharr、Canny、LOG实现边缘检测

    欢迎大家来到"Python从零到壹",在这里我将分享约200篇Python系列文章,带大家一起去学习和玩耍,看看Python这个有趣的世界.所有文章都将结合案例.代码和作者的经验讲 ...

  2. OpenCV系列之图像修补 | 五十九

    目标 在本章中, 我们将学习如何通过一种称为"修复"的方法消除旧照片中的小噪音,笔画等. 我们将看到OpenCV中的修复功能. 基础 你们大多数人家里都会有一些旧的旧化照片,上面有 ...

  3. Python编程基础:第五十九节 守护线程Daemon Threading

    第五十九节 守护线程Daemon Threading 前言 实践 前言 守护线程是在后台运行的线程,对程序的运行并不重要,你的程序在退出前不会等待守护线程的完成,此类线程的特点是,当程序中主线程及所有 ...

  4. [Python从零到壹] 五十五.图像增强及运算篇之图像平滑(均值滤波、方框滤波、高斯滤波)

    又是一年1024,首先,祝大家节日快乐! 欢迎大家来到"Python从零到壹",在这里我将分享约200篇Python系列文章,带大家一起去学习和玩耍,看看Python这个有趣的世界 ...

  5. [Python从零到壹] 五十八.图像增强及运算篇之图像锐化Sobel、Laplacian算子实现边缘检测

    欢迎大家来到"Python从零到壹",在这里我将分享约200篇Python系列文章,带大家一起去学习和玩耍,看看Python这个有趣的世界.所有文章都将结合案例.代码和作者的经验讲 ...

  6. [Python从零到壹] 五十四.图像增强及运算篇之局部直方图均衡化和自动色彩均衡化处理

    首先,祝大家教师节和中秋节快乐! 欢迎大家来到"Python从零到壹",在这里我将分享约200篇Python系列文章,带大家一起去学习和玩耍,看看Python这个有趣的世界.所有文 ...

  7. [Python从零到壹] 三十九.图像处理基础篇之图像几何变换(镜像仿射透视)

    欢迎大家来到"Python从零到壹",在这里我将分享约200篇Python系列文章,带大家一起去学习和玩耍,看看Python这个有趣的世界.所有文章都将结合案例.代码和作者的经验讲 ...

  8. [Python从零到壹] 四十九.图像增强及运算篇之顶帽运算和底帽运算

    欢迎大家来到"Python从零到壹",在这里我将分享约200篇Python系列文章,带大家一起去学习和玩耍,看看Python这个有趣的世界.所有文章都将结合案例.代码和作者的经验讲 ...

  9. [Python从零到壹] 五十六.图像增强及运算篇之图像平滑(中值滤波、双边滤波)

    欢迎大家来到"Python从零到壹",在这里我将分享约200篇Python系列文章,带大家一起去学习和玩耍,看看Python这个有趣的世界.所有文章都将结合案例.代码和作者的经验讲 ...

  10. [Python从零到壹] 五十二.图像增强及运算篇之图像掩膜直方图和HS直方图

    欢迎大家来到"Python从零到壹",在这里我将分享约200篇Python系列文章,带大家一起去学习和玩耍,看看Python这个有趣的世界.所有文章都将结合案例.代码和作者的经验讲 ...

最新文章

  1. MySQL高级能量预警
  2. 在Web界面中实现Excel数据大量导入的处理方式
  3. 【干货】工作邮件高段位写法
  4. 剪了 20% 的刘海、120Hz 刷新率、1TB 存储,iPhone 13 来了!
  5. oracle提升,Oracle特权提升
  6. lua怎么嵌入php,linux下安装php的lua扩展
  7. 第八界中国云计算大会---简单回忆
  8. POJ1001 —— Exponentiation(高精度幂问题)
  9. SnagIt - 官方网站
  10. 利用JS实现简单的注册界面验证小案例
  11. 太平洋车险条款 太平洋保险 条款 中国保险机动车交通事故责任强制保险条款 中国保险行业协会机动车综合商业保险示范条款 中国太平洋财产保险股份有限公司神行车保机动车损失保险(IACJQL0001)条款
  12. LeetCode 0799. 香槟塔
  13. 【SEBAL模型】地面特征参数反演01--大气透射率
  14. 我为什么选择使用Go语言?
  15. Qt GraphicsItem 通过直线图元连接其他两个图元
  16. 评价页面html代码,HTML5 评论列表界面模板
  17. APPLE Bonjour服务导致公司网络核心Cisco 6509崩溃的案例
  18. vsftp配置详解篇
  19. 【WebGIS全栈】从0到1开发整站——旅游足迹地图网站
  20. MYSQL数据库四种储存引擎

热门文章

  1. 在linux中怎么装python3环境,在Linux环境下安装Python3
  2. linux 访问samba共享文件夹权限,请教:linux下 利用samba网络共享文件夹修改权限的问题...
  3. c++svd算法_AI算法工程师面试6
  4. aspx调试的时候其他机器也可以打开_VSCode 穿越跳板机调试远程代码
  5. C语言之文件读写探究(七):随机读写文件
  6. 解析器 java_Java高性能解析器实现思路及方法学习
  7. mysql profiling_MySQL Profiling 的使用
  8. 去除dataframe中的空行_Python数据分析中的处理与数值加速技巧简介
  9. android tv的冷启动,YunOS智能电视操作系统——10秒快速冷启动开机
  10. 开源框架_跨平台开源框架对比介绍