当前位置: 首页 > news >正文

网站建设公司那记号网站的做代理商

网站建设公司那记号,网站的做代理商,网络广告营销案例有哪些,网站建设遵循的原则是什么1 光流法简介 光流#xff08;Optical Flow#xff09;是指图像中像素灰度值随时间的变化而产生的运动场。 简单来说#xff0c;它描述了图像中每个像素点的运动速度和方向。 光流法是一种通过分析图像序列中像素灰度值来计算光流的方法。对于图像数据计算出来的光流是一个二…1 光流法简介 光流Optical Flow是指图像中像素灰度值随时间的变化而产生的运动场。 简单来说它描述了图像中每个像素点的运动速度和方向。 光流法是一种通过分析图像序列中像素灰度值来计算光流的方法。对于图像数据计算出来的光流是一个二维向量场。比如Opencv官方给的示例图该图中显示了一个连续运动的光点箭头的方向表示光流的方向箭头的大小表示光流的大小。有了光流场我们就可以利用光流场来跟踪图像中的目标物体就可以进行运动跟踪目标检测视频压缩运动分割三维重建等。 光流法基于以下基本假设 亮度恒定就是同一点随着时间的变化其亮度不会发生改变。小运动假设Small Motion Assumption 相邻帧之间的运动是微小的足以进行线性近似。 假设每两帧画面之间的时间间隔为 Δ t \Delta t Δt且运动很小通过泰勒级数展开有 I ( x Δ x , y Δ y , t Δ t ) I ( x , y , t ) ∂ I ∂ x Δ x ∂ I ∂ y Δ y ∂ I ∂ t Δ t R ( x , y , t ) \begin{aligned} {\displaystyle I(x\Delta x,y\Delta y,t\Delta t)I(x,y,t){\frac {\partial I}{\partial x}}\Delta x{\frac {\partial I}{\partial y}}\Delta y{\frac {\partial I}{\partial t}}\Delta t} R(x,y,t) \end{aligned} I(xΔx,yΔy,tΔt)I(x,y,t)∂x∂I​Δx∂y∂I​Δy∂t∂I​ΔtR(x,y,t)​ 其中 I ( x , y , t ) I(x, y, t) I(x,y,t) 表示图像在点 ( x , y ) (x, y) (x,y) 处的灰度值 t t t 表示时间 Δ x \Delta x Δx、 Δ y \Delta y Δy 和 Δ t \Delta t Δt 分别表示水平、垂直和时间上的位移 R ( x , y , t ) R(x, y, t) R(x,y,t) 表示泰勒级数展开的高阶项。根据光流法的基本假设有 I ( x Δ x , y Δ y , t Δ t ) I ( x , y , t ) I(x\Delta x,y\Delta y,t\Delta t)I(x,y,t) I(xΔx,yΔy,tΔt)I(x,y,t) 由于泰勒高阶项趋近于0直接忽略则有 ∂ I ∂ x Δ x ∂ I ∂ y Δ y ∂ I ∂ t Δ t 0 {\displaystyle {\frac {\partial I}{\partial x}}\Delta x{\frac {\partial I}{\partial y}}\Delta y{\frac {\partial I}{\partial t}}\Delta t0} ∂x∂I​Δx∂y∂I​Δy∂t∂I​Δt0   等价为 ∂ I ∂ x Δ x Δ t ∂ I ∂ y Δ y Δ t ∂ I ∂ t Δ t Δ t 0 {\displaystyle {\frac {\partial I}{\partial x}}{\frac {\Delta x}{\Delta t}}{\frac {\partial I}{\partial y}}{\frac {\Delta y}{\Delta t}}{\frac {\partial I}{\partial t}}{\frac {\Delta t}{\Delta t}}0} ∂x∂I​ΔtΔx​∂y∂I​ΔtΔy​∂t∂I​ΔtΔt​0   其中 Δ t \Delta t Δt 表示时间间隔 Δ x \Delta x Δx 和 Δ y \Delta y Δy 分别表示水平和垂直上的位移。则 ∂ I ∂ x V x ∂ I ∂ y V y ∂ I ∂ t 0 {\displaystyle {\frac {\partial I}{\partial x}}V_{x}{\frac {\partial I}{\partial y}}V_{y}{\frac {\partial I}{\partial t}}0} ∂x∂I​Vx​∂y∂I​Vy​∂t∂I​0   其中 V x V_x Vx​ 和 V y V_y Vy​ 分别表示光流在水平和垂直方向上的分量。则我们需要求解的问题为 I x V x I y V y − I t {\displaystyle I_{x}V_{x}I_{y}V_{y}-I_{t}} Ix​Vx​Iy​Vy​−It​   简化为 ∇ I T ⋅ V ⃗ − I t {\displaystyle \nabla I^{T}\cdot {\vec {V}}-I_{t}} ∇IT⋅V −It​ 2 传统算法 2.1.1 Lucas-Kanade光流法 Lucas-Kanade 方法是一种广泛使用的光流估计微分方法由 Bruce D. Lucas 和Takeo Kanade开发。该方法假设光流在所考虑像素的局部邻域中基本恒定并根据最小二乘准则求解该邻域内所有像素的基本光流方程。   LK光流法基于以下假设 小运动假设Small Motion Assumption 相邻帧之间的运动是微小的足以进行线性近似。亮度恒定就是同一点随着时间的变化其亮度不会发生改变。空间一致性场景中相同表面的相邻点具有相似的运动并且其投影到图像平面上的距离也比较近。一个场景上邻近的点投影到图像上也是邻近点且邻近点速度一致。 前两个假设是基于泰勒展开的是所有传统光流法的基础。根据前两个假设前面已经推导过需要求解 ∇ I T ⋅ V ⃗ − I t {\displaystyle \nabla I^{T}\cdot {\vec {V}}-I_{t}} ∇IT⋅V −It​ 空间一致性假设邻域光流相似假设   针对第三个假设我们可以假设在一个大小为 w × w w \times w w×w 的窗口内所有像素点的光流都相同。则有 I x ( q 1 ) V x I y ( q 1 ) V y − I t ( q 1 ) I x ( q 2 ) V x I y ( q 2 ) V y − I t ( q 2 ) ⋮ I x ( q n ) V x I y ( q n ) V y − I t ( q n ) {\displaystyle {\begin{aligned}I_{x}(q_{1})V_{x}I_{y}(q_{1})V_{y}-I_{t}(q_{1})\\I_{x}(q_{2})V_{x}I_{y}(q_{2})V_{y}-I_{t}(q_{2})\\\;\ \vdots \\I_{x}(q_{n})V_{x}I_{y}(q_{n})V_{y}-I_{t}(q_{n})\end{aligned}}} Ix​(q1​)Vx​Iy​(q1​)Vy​Ix​(q2​)Vx​Iy​(q2​)Vy​Ix​(qn​)Vx​Iy​(qn​)Vy​​−It​(q1​)−It​(q2​) ⋮−It​(qn​)​ 其中 q 1 , q 2 , ⋯ , q n q_{1}, q_{2}, \cdots, q_{n} q1​,q2​,⋯,qn​ 表示窗口内的像素点 I x ( q ) I_{x}(q) Ix​(q) 和 I y ( q ) I_{y}(q) Iy​(q) 表示窗口内像素点的梯度 I t ( q ) I_{t}(q) It​(q) 表示窗口内像素点灰度梯度。将该公式表示为矩阵形式为 A v b {\displaystyle Avb} Avb A [ I x ( q 1 ) I y ( q 1 ) I x ( q 2 ) I y ( q 2 ) ⋮ ⋮ I x ( q n ) I y ( q n ) ] v [ V x V y ] b [ − I t ( q 1 ) − I t ( q 2 ) ⋮ − I t ( q n ) ] {\displaystyle A{\begin{bmatrix}I_{x}(q_{1})I_{y}(q_{1})\\[10pt]I_{x}(q_{2})I_{y}(q_{2})\\[10pt]\vdots \vdots \\[10pt]I_{x}(q_{n})I_{y}(q_{n})\end{bmatrix}}\quad \quad \quad v{\begin{bmatrix}V_{x}\\[10pt]V_{y}\end{bmatrix}}\quad \quad \quad b{\begin{bmatrix}-I_{t}(q_{1})\\[10pt]-I_{t}(q_{2})\\[10pt]\vdots \\[10pt]-I_{t}(q_{n})\end{bmatrix}}} A ​Ix​(q1​)Ix​(q2​)⋮Ix​(qn​)​Iy​(q1​)Iy​(q2​)⋮Iy​(qn​)​ ​v ​Vx​Vy​​ ​b ​−It​(q1​)−It​(q2​)⋮−It​(qn​)​ ​ 该系统方程组的数量多于未知数的数量无法直接求解。因此我们可以使用最小二乘来求解数值解得到 v ( A T A ) − 1 A T b {\displaystyle v\left(A^{T}A\right)^{-1}A^{T}b} v(ATA)−1ATb   其矩阵形式为 [ V x V y ] [ ∑ i I x ( q i ) 2 ∑ i I x ( q i ) I y ( q i ) ∑ i I y ( q i ) I x ( q i ) ∑ i I y ( q i ) 2 ] − 1 [ − ∑ i I x ( q i ) I t ( q i ) − ∑ i I y ( q i ) I t ( q i ) ] {\displaystyle {\begin{bmatrix}V_{x}\\[10pt]V_{y}\end{bmatrix}}{\begin{bmatrix}\sum _{i}I_{x}(q_{i})^{2}\sum _{i}I_{x}(q_{i})I_{y}(q_{i})\\[10pt]\sum _{i}I_{y}(q_{i})I_{x}(q_{i})\sum _{i}I_{y}(q_{i})^{2}\end{bmatrix}}^{-1}{\begin{bmatrix}-\sum _{i}I_{x}(q_{i})I_{t}(q_{i})\\[10pt]-\sum _{i}I_{y}(q_{i})I_{t}(q_{i})\end{bmatrix}}} ​Vx​Vy​​ ​ ​∑i​Ix​(qi​)2∑i​Iy​(qi​)Ix​(qi​)​∑i​Ix​(qi​)Iy​(qi​)∑i​Iy​(qi​)2​ ​−1 ​−∑i​Ix​(qi​)It​(qi​)−∑i​Iy​(qi​)It​(qi​)​ ​ 为了方程 A T A v A T b {\displaystyle A^{T}AvA^{T}b} ATAvATb可解 A T A {\displaystyle A^{T}A} ATA应该是可逆的或者 A T A {\displaystyle A^{T}A} ATA的特征值满足 λ 1 ≥ λ 2 0 {\displaystyle \lambda _{1}\geq \lambda _{2}0} λ1​≥λ2​0。为了避免噪音问题通常 λ 2 {\displaystyle \lambda _{2}} λ2​不能太小。另外如果 λ 1 / λ 2 {\displaystyle \lambda _{1}/\lambda _{2}} λ1​/λ2​太大这意味着点 页 p {\displaystyle p} p位于边缘容易导致多孔径问题即不同方向的光流观察到的结果一致而无法确认光流的方向。因此为了使该方法正常工作条件是 λ 1 {\displaystyle \lambda _{1}} λ1​和 λ 2 {\displaystyle \lambda _{2}} λ2​足够大且具有相似的量级。这个条件也是角点检测的条件。这项观察表明通过检查单个图像可以轻松判断哪个像素适合使用 Lucas-Kanade 方法。 算法改进   LK光流假设相同点在相邻帧画面中移动租足够小但是在实际场景中很多时候光流是很大的因此需要对LK光流法进行改进。其中一种改进方法就是引入图像金字塔的多尺度处理。使用图像金字塔改进 LK 光流算法的主要思想是 解决大位移问题 传统的 LK 光流算法基于小运动假设当图像中存在大位移运动时算法的精度会下降。 通过使用图像金字塔可以将大位移运动分解为多个小位移运动从而提高算法的精度。由粗到精的策略 首先在金字塔的顶层低分辨率图像估计光流然后在金字塔的下一层较高分辨率图像对光流进行细化以此类推直到金字塔的底层原始图像。 这种由粗到精的策略可以有效地减少计算量并提高算法的鲁棒性。 基本步骤为 构建图像金字塔 对连续的两帧图像分别构建图像金字塔。初始化光流 在金字塔的顶层将光流初始化为零。由粗到精的光流估计 从金字塔的顶层开始逐层向下进行光流估计和细化 光流估计 在当前层使用 LK 光流算法估计光流。光流上采样 将当前层的光流上采样到下一层作为下一层光流的初始值。图像扭曲 (Warping) 使用当前层的光流对下一帧图像进行扭曲使得两帧图像更加对齐。光流细化 在下一层使用 LK 光流算法对光流进行细化。 重复步骤 3直到金字塔的底层。 实践 import cv2 import numpy as npdef visualize_lk_optical_flow(video_path):使用金字塔 LK 光流算法预览视频的光流场。Args:video_path (str): 视频文件的路径。cap cv2.VideoCapture(video_path)if not cap.isOpened():print(f无法打开视频文件: {video_path})returnret, old_frame cap.read()if not ret:print(无法读取视频的第一帧。)returnold_gray cv2.cvtColor(old_frame, cv2.COLOR_BGR2GRAY)# Shi-Tomasi 角点检测参数feature_params dict(maxCorners100,qualityLevel0.3,minDistance7,blockSize7)# LK 光流参数lk_params dict(winSize(15, 15),maxLevel2,criteria(cv2.TERM_CRITERIA_EPS | cv2.TERM_CRITERIA_COUNT, 10, 0.03))# 创建随机颜色用于绘制轨迹color np.random.randint(0, 255, (100, 3))# 检测 Shi-Tomasi 角点p0 cv2.goodFeaturesToTrack(old_gray, maskNone, **feature_params)# 确保 p0 的数据类型和形状正确if p0 is not None:p0 np.float32(p0)# 创建一个 mask 用于绘制光流轨迹mask np.zeros_like(old_frame)while True:ret, frame cap.read()if not ret:breakframe_gray cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)# 计算光流if p0 is not None: # 确保有角点可以跟踪p1, st, err cv2.calcOpticalFlowPyrLK(old_gray, frame_gray, p0, None, **lk_params)# 选择好的跟踪点if p1 is not None: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, (int(a), int(b)), (int(c), int(d)), color[i].tolist(), 2)frame cv2.circle(frame, (int(a), int(b)), 5, color[i].tolist(), -1)img cv2.add(frame, mask)cv2.imshow(LK 光流, img)k cv2.waitKey(30) 0xffif k 27:break# 更新前一帧和跟踪点old_gray frame_gray.copy()p0 good_new.reshape(-1, 1, 2)else:# 如果没有跟踪点重新检测角点p0 cv2.goodFeaturesToTrack(old_gray, maskNone, **feature_params)if p0 is not None:p0 np.float32(p0)mask np.zeros_like(old_frame) # 清空 maskcap.release()cv2.destroyAllWindows()if __name__ __main__:video_path B:/Code/TestForLearn/Src/PyTest/ImageProcess/videos/3.mp4 # 替换为你的视频文件路径visualize_lk_optical_flow(video_path)2.1.2 Farneback光流法 Farneback光流法不同于LK光流法其是基于特征点的稠密光流法其基于图像金字塔和多尺度处理。 稠密光流意味着它为图像中的每个像素都计算一个运动矢量。 Farneback 算法特别之处在于它使用多项式展开来近似图像的局部邻域从而估计运动。 Farneback 算法的核心思想是使用二次多项式来近似每个像素的局部邻域的亮度分布。 对于图像中的每个像素 (x, y)其邻域的亮度值 I(x, y) 可以用以下二次多项式表示 I ( x , y ) ≈ x T ∗ A ∗ x b T ∗ x c I(x, y) ≈ x^T * A * x b^T * x c I(x,y)≈xT∗A∗xbT∗xc x [ x , y ] T x [x, y]^T x[x,y]T是像素坐标的向量。 A A A 是一个 2x2 的矩阵表示二次项系数。 b b b 是一个 2x1 的向量表示一次项系数。 c c c 是一个标量表示常数项。 算法通过最小二乘法在每个像素的局部邻域内拟合这个二次多项式。 这就得到了每个像素的 A A A、 b b b 和 c c c。假设在时间 t t t 和 t d t t dt tdt 的两个相邻帧中同一个像素的亮度保持不变亮度恒定假设。 那么对于时间 t t t 的像素 ( x , y ) (x, y) (x,y) 和时间 t d t t dt tdt 的像素 ( x d x , y d y ) (x dx, y dy) (xdx,ydy)有 I ( x , y , t ) I ( x d x , y d y , t d t ) I(x, y, t) I(x dx, y dy, t dt) I(x,y,t)I(xdx,ydy,tdt) 将这个假设应用到多项式展开中并进行一系列数学推导涉及泰勒展开和线性化可以得到一个线性方程组用于求解像素的运动矢量 ( d x , d y ) (dx, dy) (dx,dy)。 这个线性方程组可以表示为 [ A 1 A 2 ] ∗ d − 0.5 ∗ ( b 1 − b 2 ) [A_1 A_2] * d -0.5 * (b_1 - b_2) [A1​A2​]∗d−0.5∗(b1​−b2​) 其中 A 1 A_1 A1​ 和 b 1 b_1 b1​ 是时间 t t t 的帧中像素 ( x , y ) (x, y) (x,y) 的多项式系数。 A 2 A_2 A2​ 和 b 2 b_2 b2​ 是时间 t d t t dt tdt 的帧中像素 ( x , y ) (x, y) (x,y) 的多项式系数。 d [ d x , d y ] T d [dx, dy]^T d[dx,dy]T 是运动矢量。 通过求解这个线性方程组可以得到每个像素的运动矢量 ( d x , d y ) (dx, dy) (dx,dy)即光流。 实践 import cv2 import numpy as npdef visualize_farneback_optical_flow_to_mp4(video_path, output_mp4_path):使用 Farneback 光流算法预览视频的光流场并将结果保存为 MP4 视频文件。Args:video_path (str): 视频文件的路径。output_mp4_path (str): 输出 MP4 文件的路径。cap cv2.VideoCapture(video_path)if not cap.isOpened():print(f无法打开视频文件: {video_path})returnret, frame cap.read()if not ret:print(无法读取视频的第一帧。)returnheight, width frame.shape[:2]fps cap.get(cv2.CAP_PROP_FPS)# 定义 VideoWriter 对象fourcc cv2.VideoWriter_fourcc(*mp4v) # 或使用 XVIDout cv2.VideoWriter(output_mp4_path, fourcc, fps, (width, height))prvs cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)hsv np.zeros_like(frame)hsv[..., 1] 255while True:ret, frame cap.read()if not ret:breaknext cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)flow cv2.calcOpticalFlowFarneback(prvs, next, None, 0.5, 3, 15, 3, 5, 1.2, 0)mag, ang cv2.cartToPolar(flow[..., 0], flow[..., 1])hsv[..., 0] ang * 180 / np.pi / 2hsv[..., 2] cv2.normalize(mag, None, 0, 255, cv2.NORM_MINMAX)bgr cv2.cvtColor(hsv, cv2.COLOR_HSV2BGR)out.write(bgr) # 写入帧到视频文件cv2.imshow(Farneback 光流, bgr)k cv2.waitKey(30) 0xffif k 27:breakelif k ord(s):cv2.imwrite(opticalfb.png, frame)cv2.imwrite(opticalhsv.png, bgr)prvs nextcap.release()out.release()cv2.destroyAllWindows()print(f光流 MP4 已保存到: {output_mp4_path})if __name__ __main__:video_path Src/PyTest/ImageProcess/videos/3.mp4 # 替换为你的视频文件路径output_mp4_path Src/PyTest/ImageProcess/videos/farneback_optical_flow.mp4 # 替换为你想保存 MP4 的路径visualize_farneback_optical_flow_to_mp4(video_path, output_mp4_path)2.1.3 Horn光流法 Horn-Schunck 算法是一种全局光流估计方法它试图在整个图像范围内最小化一个能量函数以获得平滑且符合亮度恒定假设的光流场。 与局部方法如 Lucas-Kanade不同Horn-Schunck 算法考虑了整个图像的全局信息因此对噪声和光照变化具有更强的鲁棒性。   Horn算法假设整个图像的光流都是平滑的。因此它会尽量减少光流的扭曲并优先选择那些更平滑的解。该流被表述为一个全局能量函数然后寻求最小化。对于二维图像流该函数如下 E ∬ [ ( I x u I y v I t ) 2 α 2 ( ∥ ∇ u ∥ 2 ∥ ∇ v ∥ 2 ) ] d x d y {\displaystyle E\iint \left[(I_{x}uI_{y}vI_{t})^{2}\alpha ^{2}(\lVert \nabla u\rVert ^{2}\lVert \nabla v\rVert ^{2})\right]{{\rm {d}}x{\rm {d}}y}} E∬[(Ix​uIy​vIt​)2α2(∥∇u∥2∥∇v∥2)]dxdy I x I_x Ix​和 I y I_y Iy​是图像的梯度。 I t I_t It​是时间导数。 u u u和 v v v是光流场的分量。 α \alpha α是平滑项的权重。 该函数可以通过求解相关的多维欧拉-拉格朗日方程来最小化。这些方程是 ∂ E ∂ u − ∂ ∂ x ∂ E ∂ u x − ∂ ∂ y ∂ E ∂ u y 0 ∂ E ∂ v − ∂ ∂ x ∂ E ∂ v x − ∂ ∂ y ∂ E ∂ v y 0 \begin{aligned} {\displaystyle {\frac {\partial E}{\partial u}}-{\frac {\partial }{\partial x}}{\frac {\partial E}{\partial u_{x}}}-{\frac {\partial }{\partial y}}{\frac {\partial E}{\partial u_{y}}}0} \\ {\displaystyle {\frac {\partial E}{\partial v}}-{\frac {\partial }{\partial x}}{\frac {\partial E}{\partial v_{x}}}-{\frac {\partial }{\partial y}}{\frac {\partial E}{\partial v_{y}}}0} \end{aligned} ∂u∂E​−∂x∂​∂ux​∂E​−∂y∂​∂uy​∂E​0∂v∂E​−∂x∂​∂vx​∂E​−∂y∂​∂vy​∂E​0​ L {\displaystyle L} L是能量表达式的被积函数得出 I x ( I x u I y v I t ) − α 2 Δ u 0 I y ( I x u I y v I t ) − α 2 Δ v 0 \begin{aligned} {\displaystyle I_{x}(I_{x}uI_{y}vI_{t})-\alpha ^{2}\Delta u0}\\ {\displaystyle I_{y}(I_{x}uI_{y}vI_{t})-\alpha ^{2}\Delta v0} \end{aligned} Ix​(Ix​uIy​vIt​)−α2Δu0Iy​(Ix​uIy​vIt​)−α2Δv0​ 在实践中拉普拉斯算子可以用有限差分进行数值近似可以写成 Δ u ( x , y ) ( u ‾ ( x , y ) − u ( x , y ) ) {\displaystyle \Delta u(x,y)({\overline {u}}(x,y)-u(x,y))} Δu(x,y)(u(x,y)−u(x,y)) u ‾ ( x , y ) {\displaystyle {\overline {u}}(x,y)} u(x,y)是加权平均值 u {\displaystyle u} u在$位置 ( x , y ) (x,y) (x,y) 处像素周围的邻域内计算。使用这个符号上述方程组可以写成 ( I x 2 α 2 ) u I x I y v α 2 u ‾ − I x I t I x I y u ( I y 2 α 2 ) v α 2 v ‾ − I y I t \begin{aligned} {\displaystyle (I_{x}^{2}\alpha ^{2})uI_{x}I_{y}v\alpha ^{2}{\overline {u}}-I_{x}I_{t}}\\ {\displaystyle I_{x}I_{y}u(I_{y}^{2}\alpha ^{2})v\alpha ^{2}{\overline {v}}-I_{y}I_{t}} \end{aligned} (Ix2​α2)uIx​Iy​vα2u−Ix​It​Ix​Iy​u(Iy2​α2)vα2v−Iy​It​​ 这是线性的 u {\displaystyle u} u和 v {\displaystyle v} v并且可以针对图像中的每个像素进行求解。然而由于解依赖于流场的相邻值因此在更新相邻值后必须重复求解。以下迭代方案是利用克莱姆规则推导出来的 u k 1 u ‾ k − I x ( I x u ‾ k I y v ‾ k I t ) α 2 I x 2 I y 2 v k 1 v ‾ k − I y ( I x u ‾ k I y v ‾ k I t ) α 2 I x 2 I y 2 \begin{aligned} {\displaystyle u^{k1}{\overline {u}}^{k}-{\frac {I_{x}(I_{x}{\overline {u}}^{k}I_{y}{\overline {v}}^{k}I_{t})}{\alpha ^{2}I_{x}^{2}I_{y}^{2}}}}\\ {\displaystyle v^{k1}{\overline {v}}^{k}-{\frac {I_{y}(I_{x}{\overline {u}}^{k}I_{y}{\overline {v}}^{k}I_{t})}{\alpha ^{2}I_{x}^{2}I_{y}^{2}}}} \end{aligned} uk1uk−α2Ix2​Iy2​Ix​(Ix​ukIy​vkIt​)​vk1vk−α2Ix2​Iy2​Iy​(Ix​ukIy​vkIt​)​​    u ‾ k {\displaystyle {\overline {u}}^{k}} uk和 v ‾ k {\displaystyle {\overline {v}}^{k}} vk是 u {\displaystyle u} u和 v {\displaystyle v} v的平均值。 实践 import cv2 import numpy as np from scipy.ndimage.filters import convolve as filter2 import os from argparse import ArgumentParser see readme for running instructions def show_image(name, image):if image is None:returncv2.imshow(name, image)cv2.waitKey(0)cv2.destroyAllWindows()#compute magnitude in each 8 pixels. return magnitude average def get_magnitude(u, v):scale 3sum 0.0counter 0.0for i in range(0, u.shape[0], 8):for j in range(0, u.shape[1],8):counter 1dy v[i,j] * scaledx u[i,j] * scalemagnitude (dx**2 dy**2)**0.5sum magnitudemag_avg sum / counterreturn mag_avgdef visualize_optical_flow(u, v, img):h, w img.shape[:2]hsv np.zeros((h, w, 3), dtypenp.uint8)magnitude, angle cv2.cartToPolar(u, v)hsv[..., 0] angle * 180 / np.pi / 2hsv[..., 1] 255hsv[..., 2] cv2.normalize(magnitude, None, 0, 255, cv2.NORM_MINMAX)bgr cv2.cvtColor(hsv, cv2.COLOR_HSV2BGR)return bgr#compute derivatives of the image intensity values along the x, y, time def get_derivatives(img1, img2):#derivative masksx_kernel np.array([[-1, 1], [-1, 1]]) * 0.25y_kernel np.array([[-1, -1], [1, 1]]) * 0.25t_kernel np.ones((2, 2)) * 0.25fx filter2(img1,x_kernel) filter2(img2,x_kernel)fy filter2(img1, y_kernel) filter2(img2, y_kernel)ft filter2(img1, -t_kernel) filter2(img2, t_kernel)return [fx,fy, ft]#input: images name, smoothing parameter, tolerance #output: images variations (flow vectors u, v) #calculates u,v vectors and draw quiver def computeHS(beforeImg, afterImg, alpha, delta):beforeImg beforeImg.astype(float)afterImg afterImg.astype(float)#removing noisebeforeImg cv2.GaussianBlur(beforeImg, (5, 5), 0)afterImg cv2.GaussianBlur(afterImg, (5, 5), 0)# set up initial valuesu np.zeros((beforeImg.shape[0], beforeImg.shape[1]))v np.zeros((beforeImg.shape[0], beforeImg.shape[1]))fx, fy, ft get_derivatives(beforeImg, afterImg)avg_kernel np.array([[1 / 12, 1 / 6, 1 / 12],[1 / 6, 0, 1 / 6],[1 / 12, 1 / 6, 1 / 12]], float)iter_counter 0while True:iter_counter 1u_avg filter2(u, avg_kernel)v_avg filter2(v, avg_kernel)p fx * u_avg fy * v_avg ftd 4 * alpha**2 fx**2 fy**2prev uu u_avg - fx * (p / d)v v_avg - fy * (p / d)diff np.linalg.norm(u - prev, 2)#converges check (at most 300 iterations)if diff delta or iter_counter 300:# print(iteration number: , iter_counter)breakreturn [u, v]if __name__ __main__:# Input and output video pathsinput_video_path Src/PyTest/ImageProcess/videos/3.mp4 # 替换为你的视频文件路径output_video_path Src/PyTest/ImageProcess/videos/horn_schunck.mp4 # 替换为你想保存 MP4 的路径# Read the input videocap cv2.VideoCapture(input_video_path)if not cap.isOpened():print(fError opening video stream or file: {input_video_path})exit()# Get video propertiesframe_width int(cap.get(3))frame_height int(cap.get(4))frame_rate cap.get(cv2.CAP_PROP_FPS)# Define the codec and create VideoWriter objectfourcc cv2.VideoWriter_fourcc(*mp4v)out cv2.VideoWriter(output_video_path, fourcc, frame_rate, (frame_width, frame_height))# Read the first frameret, frame1 cap.read()if not ret:print(Failed to read the first frame!)exit()prev_gray cv2.cvtColor(frame1, cv2.COLOR_BGR2GRAY)# Process the video frame by framewhile(True):ret, frame2 cap.read()if not ret:break# Convert to grayscalegray cv2.cvtColor(frame2, cv2.COLOR_BGR2GRAY)# Compute Horn-Schunck optical flowalpha 15delta 10**-1u, v computeHS(prev_gray, gray, alpha, delta)# Visualize the optical flowflow_vis visualize_optical_flow(u, v, prev_gray)# Write the frame to the output videoout.write(flow_vis)# Display the resulting frame#cv2.imshow(Horn-Schunck Optical Flow, flow_vis)#if cv2.waitKey(1) 0xFF ord(q):# break# Update the previous frameprev_gray gray# Release video capture and writer objectscap.release()out.release()# Destroy all the windowscv2.destroyAllWindows()print(fVideo saved to {output_video_path})3 深度学习算法 深度学习相关的光流算法有很多这里只简单介绍FlowNet。 3.1 FlowNet FlowNet 是一个开创性的工作它首次展示了使用卷积神经网络 (CNN) 直接学习光流估计的可行性。 在此之前光流估计主要依赖于传统的优化方法这些方法计算量大速度慢。 FlowNet 的出现为光流估计领域带来了新的思路并为后续的深度学习光流算法奠定了基础。 FlowNet 的核心思想是利用 CNN 强大的特征提取和学习能力直接从图像数据中学习光流的模式。 通过大量的训练数据CNN 可以学习到图像特征与光流之间的映射关系从而实现快速且相对准确的光流估计。FlowNet 包含两个主要的变体FlowNetS (Simple) 和 FlowNetC (Correlation)。 FlowNetS (Simple): 输入: 将两张连续的图像 (I1, I2) 简单地堆叠在一起形成一个 6 通道的输入。网络结构: 一个标准的 CNN 结构包含卷积层、池化层和全连接层。输出: 光流场 (u, v)其中 u 和 v 分别表示水平和垂直方向上的运动矢量。特点: 结构简单易于实现但精度相对较低。 FlowNetC (Correlation): 输入: 两张连续的图像 (I1, I2) 分别经过一个 CNN 提取特征。相关层 (Correlation Layer): 将两组特征进行相关性计算得到一个相关性图 (correlation map)。 相关性图表示了 I1 中每个像素与 I2 中所有像素之间的相似度。网络结构: 将相关性图与 I1 的特征图连接在一起输入到一个 CNN 中。输出: 光流场 (u, v)。特点: 通过相关性计算可以更好地匹配对应点从而提高精度。 FlowNet 使用监督学习的方式进行训练目标是最小化预测的光流场与真实光流场之间的误差。 常用的损失函数包括 L1 损失、L2 损失以及 EPE (End-Point Error)。EPE 是光流估计中最常用的评估指标之一它衡量的是预测光流矢量与真实光流矢量之间的欧氏距离。 对于每个像素 (x, y)EPE 定义为 E P E ( x , y ) ∣ ∣ ( u p r e d ( x , y ) , v p r e d ( x , y ) ) − ( u g t ( x , y ) , v g t ( x , y ) ) ∣ ∣ 2 EPE(x, y) || (u_{pred}(x, y), v_{pred}(x, y)) - (u_{gt}(x, y), v_{gt}(x, y)) ||_2 EPE(x,y)∣∣(upred​(x,y),vpred​(x,y))−(ugt​(x,y),vgt​(x,y))∣∣2​   其中 u p r e d ( x , y ) u_{pred}(x, y) upred​(x,y) 和 v p r e d ( x , y ) v_{pred}(x, y) vpred​(x,y) 是预测的光流场 u g t ( x , y ) u_{gt}(x, y) ugt​(x,y) 和 v g t ( x , y ) v_{gt}(x, y) vgt​(x,y) 是真实的光流场。 L1 损失是 EPE 的一种变体它使用 L1 范数来衡量光流矢量之间的差异 L 1 ( x , y ) ∣ ∣ ( u p r e d ( x , y ) , v p r e d ( x , y ) ) − ( u g t ( x , y ) , v g t ( x , y ) ) ∣ ∣ 1 L1(x, y) || (u_{pred}(x, y), v_{pred}(x, y)) - (u_{gt}(x, y), v_{gt}(x, y)) ||_1 L1(x,y)∣∣(upred​(x,y),vpred​(x,y))−(ugt​(x,y),vgt​(x,y))∣∣1​   L2 损失是 EPE 的另一种变体它使用 L2 范数来衡量光流矢量之间的差异 L 2 ( x , y ) ∣ ∣ ( u p r e d ( x , y ) , v p r e d ( x , y ) ) − ( u g t ( x , y ) , v g t ( x , y ) ) ∣ ∣ 2 L2(x, y) || (u_{pred}(x, y), v_{pred}(x, y)) - (u_{gt}(x, y), v_{gt}(x, y)) ||_2 L2(x,y)∣∣(upred​(x,y),vpred​(x,y))−(ugt​(x,y),vgt​(x,y))∣∣2​ FlowNet的优缺点 优点: 速度快: 相对于传统的优化方法FlowNet 的速度非常快可以实现实时的光流估计。端到端学习: FlowNet 可以直接从图像数据中学习光流无需手动设计特征。开创性: FlowNet 开创了深度学习光流估计的先河为后续的研究奠定了基础。 缺点: 精度较低: 相对于传统的优化方法FlowNet 的精度较低。依赖于训练数据: FlowNet 的性能 сильно зависит от качества и количества обучающих данных。泛化能力有限: FlowNet 在训练数据之外的场景中表现可能不佳。 4 总结 算法原理优点缺点适用场景LK局部恒定性小运动假设计算简单速度快易于实现对噪声敏感对大位移估计差容易受光照变化影响依赖梯度信息小运动场景光照变化不大的场景需要快速计算的场景Farnebäck多项式展开对噪声具有一定的鲁棒性可以处理一定程度的大位移计算复杂度较高对参数比较敏感运动幅度较大的场景需要较高精度的场景Horn-Schunck全局平滑性约束可以生成平滑的光流场对噪声具有一定的鲁棒性计算复杂度高速度慢容易过度平滑对光照变化敏感需要平滑光流场的场景对精度要求较高的场景深度学习算法CNN 学习图像特征与光流之间的映射关系速度快精度高可以处理复杂的场景 (遮挡、光照变化、运动模糊)需要大量的训练数据对训练数据的质量要求高泛化能力可能有限计算资源消耗较大需要高精度和高速度的场景复杂的场景例如自动驾驶、机器人和视频分析 5 参考文献 Wiki-光流法光流法–Lucas Kanade算法计算机视觉的基本原理——光流法 光流法optical flow methodsWiki-Lucas-KanadevSLAMNet三-光流法-LK光流法经典光流算法 Farneback 原理与源码解析Horn–Schunck Optical Flow with a Multi-Scale Strategy【回归本源】光流 - 传统算法FlowNet: Learning Optical Flow with Convolutional Networks
http://www.pierceye.com/news/396240/

相关文章:

  • 哈尔滨做网站的价格如何利用wordpress搭建一个发卡网
  • 商会建设网站说明网站建设属于技术活吗
  • 免费申请手机网站公司画册模板免费下载
  • 网站建设策划做一个卖货的app要多少钱
  • 泉州网站平台建设公司网站服务器出错了怎么办
  • 佛山网站设计专业手机网站模板设计软件
  • 顺德网站优化公司wordpress 去广告
  • 自己建企业网站怎么建免费大数据查询
  • 短视频素材免费下载网站江西省城乡建设厅网站
  • 西安做网站公司工资wordpress 导航 分类
  • 网站建设免费教程网页设计图片高清
  • 网站后台源代码东直门小学的网站建设
  • 无锡建设局评职称网站分析 网站
  • 宜昌需要做网站建设的公司python做调查问卷网站
  • 乐陵森大最好的seo优化公司
  • php网站开发实施方案福建建筑信息平台
  • 怎么写公司网站的文案建设网站技术公司简介
  • 陕西做网站的wordpress增加变量
  • 莒南县建设工程网站网站认证方式有几种
  • 举报网站建设自查报告相同网站名
  • 网站建设网站建设公司北京logo设计制作
  • 福州市交通建设集团有限公司 网站全国国家公示系统官网
  • 郑州网站建设蝶动2023年专升本最新政策
  • 江苏网站推广网络企业宣传画册设计公司
  • 沈阳设计网站公司哪家好个人养老保险怎么交费
  • 烟台seo网站推广如何给自己公司设计logo
  • wordpress 图片大小设置梧州网站优化公司
  • 360推广 网站建设豫建设标去哪个网站
  • 职高网站建设知识点国家免费技能培训有哪些
  • 哪个网站有帮忙做公开课课件怎么查那些人输入做网站