type
status
date
slug
summary
tags
category
icon
password
光流主要是捕捉像素和像素之间的对应关系,基本操作单位是像素。
应用场景:对应物体的像素强度(光照)、视点不会改变;相邻像素向量有相似的运动。
基本光流公式
假设 表示图像位于处在 时刻的像素值,则表示为时刻后对应像素点的位置,其变化到了处,即前后两帧对应的像素点有:
等式右边进行泰勒展开,则有:
忽略二阶无穷小项,左右两边减去有:
其中,表示了图像的梯度,即表示随时间的梯度。 ,代表了光流分别沿X轴和Y轴的变化率。
约束方程只有一个,而方程有两个未知量,因此需要进行估计 。常见的有Lucas-Kanade光流估计、密集光流估计,这是从图像梯度出发去估计光流。
此外还有基于匹配、能量、相位、神经动力学等方法去进行光流估计。
Lucas-Kanade(稀疏光流)
核心计算
LK光流假设①亮度不变;②像素周围8个点都有相同运动(即3x3的窗口大小),通过这9个点的变量方程,采用最小二乘法去估计,如下所示:
公式中要求可逆,即选取的像素点需要是一些亮度变化明显的角点。
问题
- 只能处理小范围变化,大范围变化不能跟踪?
LK优化之金字塔
当物体运动幅度很大,在图像里变化很快。金字塔分层优化的LK(以下简称PyLK)核心思想是 缩小图像尺寸 。使得原本大运动的物体,在小分辨率下也保持区域内相同运动。
算法流程
- TODO
opencv实现代码
此代码不会检查下一个关键点的正确性。因此,即使任何特征点在图像中消失,光流也有可能找到看起来接近它的下一个点。因此实际上对于稳健的跟踪,角点OpenCV 样本提供了这样一个样本,它每 5 帧查找特征点,它还对光流点进行向后检查,以仅选择好的样本
密集光流
计算帧中所有点的光流。Opencv里的代码是基于Gunnar Farneback算法(2003),其特点是基于多项式展开的双帧运动估计。
核心计算
- 假设图像输入是二维矩阵(即灰度矩阵),像素点位置为,像素值为 ,则其多项式展开为:
其中 是2x2的对称矩阵(通过像素的邻域信息的最小二乘加权拟合得到的,权重系数与邻域的像素大小和位置有关),是2x1矩阵,是偏置项
- 以上公式右侧展开:
- 将原有图像的二维信号空间,转换到以 (1,𝑥,𝑦,𝑥2,𝑦2,𝑥𝑦)作为基函数的空间
- TODO :最小二乘、权重的选择
opencv实现代码
其中cv2.calcOpticalFlowFarneback()
中参数及其含义如下
- prev:前一帧图像
- next: 后一帧图像
- flow: 输出的光流矩阵。矩阵大小同输入的图像一样大,但是矩阵中的每一个元素可不是一个值,而是两个值,分别表示这个点在x方向与y方向的运动量(偏移量)。
- pyr_scale: 金字塔上下两层之间的尺度关系
- levels: 金字塔层数
- winsize: 均值窗口大小,越大越能denoise并且能够检测快速移动目标,但会引起模糊运动区域
- iterations: 迭代次数
- poly_n: 像素领域大小,一般为5,7等
- poly_sigma: 高斯标注差,一般为1-1.5
- flags: 计算方法
参考
‣
‣
‣
‣
‣
- 作者:Wtoy
- 链接:https://blog.wtoy.top/article/2024/b9f58108-2e0e-497a-9f70-a65bb4c91968
- 声明:本文采用 CC BY-NC-SA 4.0 许可协议,转载请注明出处。