PotatoPie 4.0 实验教程(30) —— FPGA实现摄像头图像中值滤波

中值滤波是什么?

图像的中值滤波是一种非线性图像滤波方法,它用于去除图像中的椒盐噪声或其他类型的噪声。中值滤波的原理是用每个像素周围的邻域中的中值来替代该像素的值。与均值滤波不同,中值滤波不会受到极端值的影响,因此在处理存在椒盐噪声的图像时通常效果更好。

中值滤波的步骤如下:

  1. 定义邻域大小: 对于图像中的每个像素,定义一个固定大小的邻域,通常是一个正方形或矩形区域。

  2. 获取邻域像素值: 对于每个像素,获取其邻域内的像素值。

  3. 排序邻域像素值: 将邻域内的像素值按照大小进行排序,通常是从小到大或从大到小。

  4. 计算中值: 根据邻域内像素值的排序结果,找到中间位置的像素值,即中位数。

  5. 应用中值: 将中位数作为该像素的新值,用于替代原始图像中的像素值。

  6. 重复步骤: 对图像中的每个像素都重复执行上述步骤,直到整个图像都被处理过。

中值滤波的关键特点是它不受异常值的影响,因为它使用邻域内像素值的中间值来替代当前像素值,从而有效地去除噪声并保留图像的细节信息。

中值滤波是什么?

图像的中值滤波是一种非线性图像滤波方法,它用于去除图像中的椒盐噪声或其他类型的噪声。中值滤波的原理是用每个像素周围的邻域中的中值来替代该像素的值。与均值滤波不同,中值滤波不会受到极端值的影响,因此在处理存在椒盐噪声的图像时通常效果更好。

中值滤波的步骤如下:

  1. 定义邻域大小: 对于图像中的每个像素,定义一个固定大小的邻域,通常是一个正方形或矩形区域。

  2. 获取邻域像素值: 对于每个像素,获取其邻域内的像素值。

  3. 排序邻域像素值: 将邻域内的像素值按照大小进行排序,通常是从小到大或从大到小。

  4. 计算中值: 根据邻域内像素值的排序结果,找到中间位置的像素值,即中位数。

  5. 应用中值: 将中位数作为该像素的新值,用于替代原始图像中的像素值。

  6. 重复步骤: 对图像中的每个像素都重复执行上述步骤,直到整个图像都被处理过。

中值滤波的关键特点是它不受异常值的影响,因为它使用邻域内像素值的中间值来替代当前像素值,从而有效地去除噪声并保留图像的细节信息。

中值滤波的算法实现

python实现图像中值滤波的源码

PotatoPie 4.0 实验教程(30) ------ FPGA实现摄像头图像中值滤波-Anlogic-安路论坛-FPGA CPLD-ChipDebug

这段 Python 代码实现了图像处理中的几个常见操作:

  1. 从文件系统中读取名为 "Lena.jpg" 的图像文件,并将其转换为灰度图像。
  2. 实现了中值滤波函数 median_filter,用于对灰度图像进行中值滤波处理。中值滤波是一种非线性滤波器,用于去除图像中的噪声,通过用像素点周围区域的中值替换当前像素值。
  3. 实现了添加椒盐噪声的函数 add_salt_pepper_noise。椒盐噪声是一种常见的图像噪声,随机将像素点的灰度值设置为黑色或白色,模拟图像传感器中的随机错误。
  4. 使用中值滤波函数处理原始灰度图像、添加椒盐噪声后的图像以及高斯噪声后的图像,并显示处理前后的结果。

整体来说,这段代码演示了如何使用 Python 和 OpenCV 库对图像进行中值滤波处理以及添加椒盐噪声,并展示了处理前后的图像效果。

MATLAB实现图像中值滤波的源码

这段 MATLAB 代码实现了图像的中值滤波,包括对原始灰度图像、添加椒盐噪声后的图像以及添加高斯噪声后的图像进行中值滤波处理,并显示处理前后的图像。

  1. 首先,代码读取了名为 'Lena.jpg' 的图像文件,并将其转换为灰度图像。
  2. 然后,对灰度图像进行了中值滤波处理,使用的窗口大小为3×3,即对每个像素及其周围8个像素进行排序,并将中间值作为该像素的值。
  3. 接着,代码生成了添加了椒盐噪声的图像,并对其进行了相同的中值滤波处理。
  4. 最后,代码生成了添加了高斯噪声的图像,并同样进行了中值滤波处理。

在处理后,原始灰度图像、添加椒盐噪声后的图像和添加高斯噪声后的图像分别与其对应的中值滤波处理结果一起显示在一个图像窗口中,以便比较处理前后的效果。

FPGA工程分析

工程层次图

demo18 相比,只是多了一个img_med_fltr 的模块,也就是下面这一段代码,在从SDRAM读出来之后,经它处理后再输出hdmi_tx模块。

复制代码
img_med_fltr u_img_med_fltr

(

.i_clk(clk_pixel),

.i_rst_n(sys_rst_n),

.i_hs(VGA_HS),

.i_vs(VGA_VS),

.i_de(VGA_DE),

.i_r(VGA_RGB[23:16]),

.i_g(VGA_RGB[15:8] ),

.i_b(VGA_RGB[7:0] ),

.o_hs(img_med_hs),

.o_vs(img_med_vs),

.o_de(img_med_de),

.o_r(img_med_data[23:16]),

.o_g(img_med_data[15:8] ),

.o_b(img_med_data[7:0] )

);

img_med_fltr模块源代码分析

跟前面几篇教程一样,我们都需要先用行缓存将像素转化为同时输出3行3列来,后面的讲解都以R通道为例,因为其它三个通道的行为是一样的:

复制代码
// R通道行缓存
img_buf u_r_buf
(
  .i_clk    (i_clk      ),
  .i_rst_n  (i_rst_n    ),
  .i_de    (i_de      ),
  .i_data    (i_r      ),
  .o_de    (        ),
  .o_p11    (r_p_11      ),
  .o_p12    (r_p_12      ),
  .o_p13    (r_p_13      ),  
  .o_p21    (r_p_21      ),
  .o_p22    (r_p_22      ),
  .o_p23    (r_p_23      ),    
  .o_p31    (r_p_31      ),
  .o_p32    (r_p_32      ),
  .o_p33    (r_p_33      )
);

然后对像素进行排序,分成三步:

1.先按行找出同一行中的最大值,最小值,中值,即:

PotatoPie 4.0 实验教程(30) ------ FPGA实现摄像头图像中值滤波-Anlogic-安路论坛-FPGA CPLD-ChipDebug

2.从找出这三行的三个最大值中找出最大值里的最小值,同时从三行的最小值里找出最大值,还有从三行的最值里找出最中值,即:

PotatoPie 4.0 实验教程(30) ------ FPGA实现摄像头图像中值滤波-Anlogic-安路论坛-FPGA CPLD-ChipDebug

3.从第2步的值里找出最终的中值reg [7:0] r_med;

具体怎么比较,verilog代码里写得比较清楚。

管脚约束

PotatoPie 4.0 实验教程(18) ------ FPGA实现OV5640摄像头采集以SDRAM作为显存进行HDMI输出显示相同,不作赘述。

时序约束

PotatoPie 4.0 实验教程(18) ------ FPGA实现OV5640摄像头采集以SDRAM作为显存进行HDMI输出显示相同,不作赘述。

实验效果

相关推荐
ゞ 正在缓冲99%…3 小时前
leetcode2826.将三个组排序
算法·leetcode·动态规划
奋斗的牛马3 小时前
FPGA—ZYNQ学习Debug(三)
学习·fpga开发
qq_401700413 小时前
matlab学习
学习·算法·matlab
小马过河R4 小时前
AIGC视频生成之Deepseek、百度妙笔组合实战小案例
人工智能·深度学习·计算机视觉·百度·aigc
budingxiaomoli5 小时前
算法--滑动窗口(一)
数据结构·算法
王哈哈^_^5 小时前
【数据集】【YOLO】【目标检测】农作物病害数据集 11498 张,病害检测,YOLOv8农作物病虫害识别系统实战训推教程。
人工智能·深度学习·算法·yolo·目标检测·计算机视觉·1024程序员节
xier_ran5 小时前
邻接矩阵的 k 次幂意味着什么?从图论到路径计数的直观解释
算法·图论
B站_计算机毕业设计之家6 小时前
预测算法:股票数据分析预测系统 股票预测 股价预测 Arima预测算法(时间序列预测算法) Flask 框架 大数据(源码)✅
python·算法·机器学习·数据分析·flask·股票·预测
想唱rap7 小时前
C++ list 类的使用
c语言·开发语言·数据结构·c++·笔记·算法·list
Theodore_10227 小时前
神经学习(4)神经网络的向量化实现与TensorFlow训练流程
人工智能·深度学习·机器学习·计算机视觉·线性回归