opencv支持的一些计算光流的算法

2024-04-10 06:28

本文主要是介绍opencv支持的一些计算光流的算法,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

  1. Lucas-Kanade(LK)光流算法
    Lucas-Kanade(LK)光流算法是一种经典的稀疏光流算法,用于估计图像中局部区域的运动信息。它最初由Bruce D. Lucas和Takeo Kanade于1981年提出,是最早的光流估计方法之一,至今仍然被广泛应用。
    LK光流算法的基本原理是利用局部区域的像素灰度值在两帧图像中的变化来估计运动向量。具体而言,它假设了一个关于运动的线性模型,并通过最小化每个像素周围邻域的灰度值误差来求解最佳的运动向量。

算法步骤如下:

选择特征点:首先,在图像中选择一组关键的特征点或角点,通常使用角点检测算法(如Harris角点检测)来检测这些特征点。

建立窗口:对于每个选定的特征点,定义一个小的局部窗口,通常是一个矩形区域,用来捕获周围像素的灰度信息。

计算灰度梯度:在每个窗口中,计算每个像素位置处的灰度梯度,通常使用Sobel算子或其他梯度计算方法。

构建雅可比矩阵:根据当前帧和下一帧图像的灰度梯度信息,构建一个关于运动参数的雅可比矩阵,这个矩阵描述了像素灰度值对运动参数的响应。

求解运动向量:通过最小化当前帧窗口中像素灰度值与下一帧窗口中对应位置像素灰度值之间的误差(通常使用最小二乘法),来求解最佳的运动向量。

迭代优化:通常,LK算法会进行多次迭代来不断优化运动向量的估计值,直到达到收敛条件或达到最大迭代次数。

输出光流场:最终,对于每个特征点,得到其对应的运动向量,从而形成整个图像的光流场。

总的来说,Lucas-Kanade光流算法是一种经典的稀疏光流算法,适用于处理运动相对较小且区域局部性较强的图像序列,如视觉里程计、目标跟踪等任务。

import cv2# 读取视频
cap = cv2.VideoCapture('video.mp4')# 创建LK光流对象
lk_flow = cv2.optflow.createOptFlow_DeepFlow()# 读取第一帧
ret, prev_frame = cap.read()# 转换为灰度图像
prev_gray = cv2.cvtColor(prev_frame, cv2.COLOR_BGR2GRAY)# 设置角点检测参数
feature_params = dict(maxCorners=100, qualityLevel=0.3, minDistance=7, blockSize=7)# 获取第一帧的角点
prev_pts = cv2.goodFeaturesToTrack(prev_gray, mask=None, **feature_params)# 创建掩码用于绘制轨迹
mask = np.zeros_like(prev_frame)# 循环处理每一帧
while True:# 读取当前帧ret, frame = cap.read()if not ret:break# 转换为灰度图像gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)# 计算LK光流next_pts, status, _ = cv2.calcOpticalFlowPyrLK(prev_gray, gray, prev_pts, None)# 选择好的点good_next_pts = next_pts[status == 1]good_prev_pts = prev_pts[status == 1]# 绘制轨迹for i, (new, old) in enumerate(zip(good_next_pts, good_prev_pts)):a, b = new.ravel()c, d = old.ravel()mask = cv2.line(mask, (a, b), (c, d), (0, 255, 0), 2)frame = cv2.circle(frame, (a, b), 5, (0, 0, 255), -1)# 合并光流图像和原始图像img = cv2.add(frame, mask)# 更新前一帧的图像和角点prev_gray = gray.copy()prev_pts = good_next_pts.reshape(-1, 1, 2)# 显示结果cv2.imshow('Optical Flow', img)# 按 'q' 键退出循环if cv2.waitKey(25) & 0xFF == ord('q'):break# 释放资源
cap.release()
cv2.destroyAllWindows()

示例代码中,首先检测第一帧中的角点,然后利用LK光流算法跟踪这些角点的运动,并绘制出轨迹。最后,将轨迹绘制到原始图像上并显示。

  1. Farneback光流算法
    Farneback光流算法是一种基于密集光流的方法,用于估计图像序列中每个像素的运动。它由Gunnar Farneback于2003年提出,并在后续的研究中得到改进和拓展。

Farneback算法的主要思想是利用多项式展开来近似描述图像中每个像素周围的运动。具体来说,它通过对图像中局部区域进行多项式拟合来估计每个像素的运动速度和方向。

算法步骤如下:

图像金字塔构建:首先,对输入的图像序列构建高斯金字塔,这样可以处理不同尺度的运动,并使得算法对于不同尺度的运动都有较好的适应性。

密集光流计算:在每个金字塔层级上,对图像进行光流计算。Farneback算法通过计算相邻图像块之间的像素强度差异,来估计局部运动的相似性。

多项式展开:对于每个像素,使用多项式展开来逼近其周围像素的运动。这种多项式展开考虑了多个尺度上的运动信息,并能够更准确地描述局部运动的复杂性。

运动向量估计:根据多项式展开得到的参数,估计每个像素的运动速度和方向。这些参数反映了图像中每个像素的局部运动情况。

光流场重建:将每个像素的运动信息整合起来,形成完整的光流场。这个光流场描述了图像序列中每个像素的运动情况,可以用于后续的运动分析和处理任务。

总的来说,Farneback光流算法是一种基于密集光流的方法,适用于需要精细的像素级别运动信息的任务,如视频稳定、光流场估计等。它能够有效地处理图像中的复杂运动。

import cv2# 读取视频
cap = cv2.VideoCapture('video.mp4')# 创建Farneback光流对象
farneback_flow = cv2.optflow.createOptFlow_Farneback()# 创建LK光流对象
lk_flow = cv2.optflow.createOptFlow_DeepFlow()# 读取第一帧
ret, prev_frame = cap.read()# 转换为灰度图像
prev_gray = cv2.cvtColor(prev_frame, cv2.COLOR_BGR2GRAY)# 循环处理每一帧
while True:# 读取当前帧ret, frame = cap.read()if not ret:break# 转换为灰度图像gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)# 计算Farneback光流flow_farneback = farneback_flow.calc(prev_gray, gray, None)# 计算LK光流flow_lk = lk_flow.calc(prev_gray, gray, None)# 可视化光流# 这里可以根据具体需求进行可视化处理,比如画箭头表示光流方向等# 更新上一帧prev_gray = gray# 显示结果cv2.imshow('Farneback Optical Flow', frame)cv2.imshow('LK Optical Flow', frame)# 按 'q' 键退出循环if cv2.waitKey(25) & 0xFF == ord('q'):break# 释放资源
cap.release()
cv2.destroyAllWindows()
  1. ROLF光流
    RLOF(Robust Local Optical Flow)算法是一种用于计算光流(optical flow)的局部方法,旨在提高在复杂场景中的光流估计的准确性和鲁棒性。与传统的光流算法相比,RLOF算法采用了一种自适应的局部窗口策略,并且结合了稀疏和密集光流的优点。

RLOF算法的主要特点和原理包括:

自适应局部窗口:RLOF算法采用了一种自适应的局部窗口策略,可以根据图像中的像素运动情况和图像特性来动态调整窗口大小。这种自适应的窗口大小可以帮助提高在不同区域的光流估计精度,并且能够有效地处理非刚体运动和快速动态场景。

鲁棒性:RLOF算法使用了一些鲁棒的技术来提高光流估计的稳健性,如利用局部梯度信息来对光流进行加权,以减少对噪声和异常值的敏感性。

多尺度处理:为了适应不同尺度下的运动情况,RLOF算法通常会对图像进行多尺度处理,以提高光流估计的准确性和鲁棒性。

快速计算:尽管RLOF算法在提高光流估计的准确性和鲁棒性方面进行了改进,但也注重了算法的计算效率,以便在实际应用中能够实时处理图像序列。

RLOF算法在复杂场景中的光流估计任务中表现出了较好的性能,并且在实际应用中得到了广泛的应用。它在视频处理、目标跟踪、动作识别等领域都具有重要的作用。

import cv2# 读取视频
cap = cv2.VideoCapture('video.mp4')# 创建稠密光流对象
dense_flow = cv2.optflow.createOptFlow_DenseRLOF()# 读取第一帧
ret, prev_frame = cap.read()# 转换为灰度图像
prev_gray = cv2.cvtColor(prev_frame, cv2.COLOR_BGR2GRAY)# 循环处理每一帧
while True:# 读取当前帧ret, frame = cap.read()if not ret:break# 转换为灰度图像gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)# 计算光流flow = dense_flow.calc(prev_gray, gray, None)# 可视化光流# 这里可以根据具体需求进行可视化处理,比如画箭头表示光流方向等# 更新上一帧prev_gray = gray# 显示结果cv2.imshow('Optical Flow', frame)# 按 'q' 键退出循环if cv2.waitKey(25) & 0xFF == ord('q'):break# 释放资源
cap.release()
cv2.destroyAllWindows()
  1. DIS光流
    DIS(Dense Inverse Search)光流算法是一种稠密光流算法,与稀疏光流算法(如Lucas-Kanade)不同,它可以计算图像中每个像素的运动向量,而不仅仅是一些选定的特征点。这使得它更适合于一些需要更精细运动信息的任务,比如视频处理、运动分析等。其主要特点包括采用逆向搜索策略、密集采样、多尺度处理和鲁棒性技术。通过逆向搜索,在当前图像中直接搜索与参考图像中对应区域最相似的像素,以确定其光流,从而提高了计算效率。
import cv2# 读取视频
cap = cv2.VideoCapture('video.mp4')# 创建DIS光流对象
dis_flow = cv2.optflow.createOptFlow_DIS(cv2.optflow.DISOPTICAL_FLOW_PRESET_MEDIUM)# 读取第一帧
ret, prev_frame = cap.read()# 转换为灰度图像
prev_gray = cv2.cvtColor(prev_frame, cv2.COLOR_BGR2GRAY)# 循环处理每一帧
while True:# 读取当前帧ret, frame = cap.read()if not ret:break# 转换为灰度图像gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)# 计算DIS光流flow = dis_flow.calc(prev_gray, gray, None)# 可视化光流# 可以根据需要对光流进行可视化处理,例如绘制箭头表示运动方向等# 更新前一帧的灰度图像prev_gray = gray# 显示结果cv2.imshow('DIS Optical Flow', frame)# 按 'q' 键退出循环if cv2.waitKey(25) & 0xFF == ord('q'):break# 释放资源
cap.release()
cv2.destroyAllWindows()

这篇关于opencv支持的一些计算光流的算法的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/890287

相关文章

opencv实现像素统计的示例代码

《opencv实现像素统计的示例代码》本文介绍了OpenCV中统计图像像素信息的常用方法和函数,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一... 目录1. 统计像素值的基本信息2. 统计像素值的直方图3. 统计像素值的总和4. 统计非零像素的数量

如何用Java结合经纬度位置计算目标点的日出日落时间详解

《如何用Java结合经纬度位置计算目标点的日出日落时间详解》这篇文章主详细讲解了如何基于目标点的经纬度计算日出日落时间,提供了在线API和Java库两种计算方法,并通过实际案例展示了其应用,需要的朋友... 目录前言一、应用示例1、天安门升旗时间2、湖南省日出日落信息二、Java日出日落计算1、在线API2

不懂推荐算法也能设计推荐系统

本文以商业化应用推荐为例,告诉我们不懂推荐算法的产品,也能从产品侧出发, 设计出一款不错的推荐系统。 相信很多新手产品,看到算法二字,多是懵圈的。 什么排序算法、最短路径等都是相对传统的算法(注:传统是指科班出身的产品都会接触过)。但对于推荐算法,多数产品对着网上搜到的资源,都会无从下手。特别当某些推荐算法 和 “AI”扯上关系后,更是加大了理解的难度。 但,不了解推荐算法,就无法做推荐系

康拓展开(hash算法中会用到)

康拓展开是一个全排列到一个自然数的双射(也就是某个全排列与某个自然数一一对应) 公式: X=a[n]*(n-1)!+a[n-1]*(n-2)!+...+a[i]*(i-1)!+...+a[1]*0! 其中,a[i]为整数,并且0<=a[i]<i,1<=i<=n。(a[i]在不同应用中的含义不同); 典型应用: 计算当前排列在所有由小到大全排列中的顺序,也就是说求当前排列是第

使用opencv优化图片(画面变清晰)

文章目录 需求影响照片清晰度的因素 实现降噪测试代码 锐化空间锐化Unsharp Masking频率域锐化对比测试 对比度增强常用算法对比测试 需求 对图像进行优化,使其看起来更清晰,同时保持尺寸不变,通常涉及到图像处理技术如锐化、降噪、对比度增强等 影响照片清晰度的因素 影响照片清晰度的因素有很多,主要可以从以下几个方面来分析 1. 拍摄设备 相机传感器:相机传

csu 1446 Problem J Modified LCS (扩展欧几里得算法的简单应用)

这是一道扩展欧几里得算法的简单应用题,这题是在湖南多校训练赛中队友ac的一道题,在比赛之后请教了队友,然后自己把它a掉 这也是自己独自做扩展欧几里得算法的题目 题意:把题意转变下就变成了:求d1*x - d2*y = f2 - f1的解,很明显用exgcd来解 下面介绍一下exgcd的一些知识点:求ax + by = c的解 一、首先求ax + by = gcd(a,b)的解 这个

综合安防管理平台LntonAIServer视频监控汇聚抖动检测算法优势

LntonAIServer视频质量诊断功能中的抖动检测是一个专门针对视频稳定性进行分析的功能。抖动通常是指视频帧之间的不必要运动,这种运动可能是由于摄像机的移动、传输中的错误或编解码问题导致的。抖动检测对于确保视频内容的平滑性和观看体验至关重要。 优势 1. 提高图像质量 - 清晰度提升:减少抖动,提高图像的清晰度和细节表现力,使得监控画面更加真实可信。 - 细节增强:在低光条件下,抖

【数据结构】——原来排序算法搞懂这些就行,轻松拿捏

前言:快速排序的实现最重要的是找基准值,下面让我们来了解如何实现找基准值 基准值的注释:在快排的过程中,每一次我们要取一个元素作为枢纽值,以这个数字来将序列划分为两部分。 在此我们采用三数取中法,也就是取左端、中间、右端三个数,然后进行排序,将中间数作为枢纽值。 快速排序实现主框架: //快速排序 void QuickSort(int* arr, int left, int rig

poj 3974 and hdu 3068 最长回文串的O(n)解法(Manacher算法)

求一段字符串中的最长回文串。 因为数据量比较大,用原来的O(n^2)会爆。 小白上的O(n^2)解法代码:TLE啦~ #include<stdio.h>#include<string.h>const int Maxn = 1000000;char s[Maxn];int main(){char e[] = {"END"};while(scanf("%s", s) != EO

秋招最新大模型算法面试,熬夜都要肝完它

💥大家在面试大模型LLM这个板块的时候,不知道面试完会不会复盘、总结,做笔记的习惯,这份大模型算法岗面试八股笔记也帮助不少人拿到过offer ✨对于面试大模型算法工程师会有一定的帮助,都附有完整答案,熬夜也要看完,祝大家一臂之力 这份《大模型算法工程师面试题》已经上传CSDN,还有完整版的大模型 AI 学习资料,朋友们如果需要可以微信扫描下方CSDN官方认证二维码免费领取【保证100%免费