前言

光流法是计算机视觉领域非常常用的算法,深度学习时代的CV工程师可能会用到光流法,但鲜有对其实现原理做深度地探索的。今天正好趁着复现一个项目把LK光流法的算法进行一个探索和整理。

先看一个LK光流法实现的效果:代码可戳《python光流实验》

深度学习光流算法 光流法算法_深度学习光流算法


1. 问题建模

光流法是通过比较连续两帧的差异来估计运动物体移动的。
咱们先选定一个点深度学习光流算法 光流法算法_计算机视觉_02,在理论上,时间深度学习光流算法 光流法算法_深度学习光流算法_03时刻,经历过深度学习光流算法 光流法算法_Lucas-Kanade_04后,点深度学习光流算法 光流法算法_计算机视觉_02会移动到另一个位置深度学习光流算法 光流法算法_计算机视觉_06,并且深度学习光流算法 光流法算法_计算机视觉_06本身和周围都有着与深度学习光流算法 光流法算法_计算机视觉_02相似的亮度值。朴素的LK光流法是直接用灰度值代替RGB作为亮度。
根据上面的描述,对于点深度学习光流算法 光流法算法_计算机视觉_02而言,假设深度学习光流算法 光流法算法_计算机视觉_02的坐标值是深度学习光流算法 光流法算法_光流_11,有
深度学习光流算法 光流法算法_深度学习光流算法_12 深度学习光流算法 光流法算法_深度学习光流算法_13
其中,深度学习光流算法 光流法算法_深度学习光流算法_14代表点深度学习光流算法 光流法算法_计算机视觉_02在时间深度学习光流算法 光流法算法_计算机视觉_16时刻的亮度值(灰度值)。经过了时间深度学习光流算法 光流法算法_Lucas-Kanade_04以后,点深度学习光流算法 光流法算法_计算机视觉_02分别向两个轴移动了深度学习光流算法 光流法算法_光流_19深度学习光流算法 光流法算法_深度学习光流算法_20的距离。
根据泰勒公式:(咱们在这里把深度学习光流算法 光流法算法_光流法_21深度学习光流算法 光流法算法_计算机视觉_22看做是深度学习光流算法 光流法算法_计算机视觉_16的函数,把公式(1)看做单变量深度学习光流算法 光流法算法_计算机视觉_16的等式,只需对t进行展开)
深度学习光流算法 光流法算法_深度学习光流算法_25深度学习光流算法 光流法算法_光流_26
最后那一项是佩亚诺余项,更高阶,咱们可以假定为0。所以,根据公式2,我们可以得到:
深度学习光流算法 光流法算法_计算机视觉_27深度学习光流算法 光流法算法_计算机视觉_28
深度学习光流算法 光流法算法_光流法_29
深度学习光流算法 光流法算法_深度学习光流算法_30
则公式(3)可以简写成:
深度学习光流算法 光流法算法_光流_31深度学习光流算法 光流法算法_Lucas-Kanade_32
公式4,便是咱们的核心公式了。其中深度学习光流算法 光流法算法_计算机视觉_33深度学习光流算法 光流法算法_计算机视觉_34代表两个方向(x方向和y方向)的移动速度,深度学习光流算法 光流法算法_Lucas-Kanade_35深度学习光流算法 光流法算法_Lucas-Kanade_36深度学习光流算法 光流法算法_Lucas-Kanade_37代表了亮度在三个轴上的偏导(也就是梯度)。把深度学习光流算法 光流法算法_光流法_38深度学习光流算法 光流法算法_计算机视觉_39计算出来,咱们的光流也就算出来了。
拿到当前帧,假设我们要计算点深度学习光流算法 光流法算法_计算机视觉_02的光流。其中深度学习光流算法 光流法算法_光流法_41深度学习光流算法 光流法算法_光流_42都可以通过当前帧计算出来,而深度学习光流算法 光流法算法_光流法_43可以通过两帧的差分计算出来。所以,对于公式(4)而言,未知数只有深度学习光流算法 光流法算法_计算机视觉_33深度学习光流算法 光流法算法_计算机视觉_34

2.Lucas-Kanade

LK算法就是用来求解公式(4)的。LK有一个window的概念,即我先划定一块区域比如(5x5)的像素区域,我们可以认为这块区域每个点的移动速度深度学习光流算法 光流法算法_计算机视觉_33深度学习光流算法 光流法算法_计算机视觉_34是一致的。

首先,深度学习光流算法 光流法算法_光流法_41深度学习光流算法 光流法算法_光流_42是怎么得到的呢?对于光流法,咱们有个理想的假定就是:运动物体只会做平移。所以,亮度梯度咱们只需考虑当前帧的梯度即可。对于深度学习光流算法 光流法算法_光流法_43我们在两帧做一个差分就可以得到。

深度学习光流算法 光流法算法_光流_51


咱们看当前帧,也就是右边那个。深度学习光流算法 光流法算法_Lucas-Kanade_52是因为在深度学习光流算法 光流法算法_光流法_21轴的数值左右都是3,没有梯度变化。深度学习光流算法 光流法算法_计算机视觉_54是因为在深度学习光流算法 光流法算法_计算机视觉_22轴数值变化幅度为1。上图显示的情况,咱们只能算出y轴速度深度学习光流算法 光流法算法_计算机视觉_39,没有办法算出水平(x轴)速度深度学习光流算法 光流法算法_光流法_38。这是因为该移动目标本身在x轴方向上就没有亮度变化。这也是一种典型的问题,叫孔径问题(Aperture Problem)。

孔径问题是讲,如果我们通过一个小孔来看全局,很多情况下的移动信息我们是看不出来的,这个用一张图就可以很好理解:

深度学习光流算法 光流法算法_计算机视觉_58


假设墙上破了一个洞,咱们通过这个洞来看一个图形的移动情况。假设,我们看到的是上图这种情况,绿色部分就是我们的视野,我们无法判断这个图形是否是沿着切线方向移动或者是静止。听懂掌声。

那么基于小区域的LK光流法也可能遇到Aperture Problem,所以我们在追光流的时候,选点通常会选目标的角点(corner)。角点的情况如下图:

深度学习光流算法 光流法算法_深度学习光流算法_59


如果角点在视野内的话,咱们就可以判断这个图形的运动方向。听懂继续掌声。

接着公式(4),咱们如果通过window方式求解深度学习光流算法 光流法算法_光流法_38深度学习光流算法 光流法算法_计算机视觉_39,那还是很好办的。假设咱们取的是5x5的window,那么window内的每个点,我们都认为有一样的移动方向,咱们可以构建出25个等式。求解二元一次方程,通常两个等式就可以求解。但那是理想情况,实际情况是没有一组深度学习光流算法 光流法算法_光流法_62能同时满足这25个等式,咱们要做的是最小化这个差异。

深度学习光流算法 光流法算法_计算机视觉_63


写成矩阵形式:

深度学习光流算法 光流法算法_深度学习光流算法_64

只需找到一组深度学习光流算法 光流法算法_光流法_62,即上图中的深度学习光流算法 光流法算法_光流法_21,满足

深度学习光流算法 光流法算法_光流法_67深度学习光流算法 光流法算法_光流_68

这里就可以用最小二乘法来进行优化了,分别求偏导得出导数为0的点的值就是最优值。可推导出,

深度学习光流算法 光流法算法_Lucas-Kanade_69


这便是Lucas-Kanade光流算法的公式了。

参考:http://www.cs.cmu.edu/~16385/s15/lectures/Lecture21.pdf