4. 去噪算法基础:空域滤波与频域滤波
各位同学,今天我们来聊聊去噪算法的基础。这部分内容,说白了就是ISP通路上最常用的“手艺活”。我做了这么多年图像处理,发现很多新人一上来就追最新的AI去噪,结果连最基础的均值滤波都没调明白。嗯,咱们还是先把地基打牢。
去噪算法,按处理域来分,主要就是两大类:空域滤波和频域滤波。空域滤波直接操作像素,频域滤波则先把图像变换到频率空间再处理。各有各的脾气,咱们一个一个说。
4.1 空域滤波:最朴素的去噪手段
空域滤波,说白了就是用一个“窗口”在图像上滑动,对窗口内的像素做某种数学运算。你想想看,这就像用一个刷子在画布上抹,抹得均匀了,噪点就淡了。
4.1.1 均值滤波
均值滤波是最简单的。取一个3x3或5x5的窗口,把里面所有像素值加起来求平均,然后用这个平均值替代中心像素。
// 3x3均值滤波核
[1/9, 1/9, 1/9]
[1/9, 1/9, 1/9]
[1/9, 1/9, 1/9]
我在项目中遇到过一个问题:用均值滤波去噪,图像是平滑了,但边缘也糊了。为什么呢?因为均值滤波把边缘两侧的像素也混在一起了。说白了,它不分青红皂白,所有像素一视同仁。
4.1.2 高斯滤波
高斯滤波比均值滤波聪明一点。它给窗口内的像素分配不同的权重——离中心越近,权重越大;离中心越远,权重越小。权重分布服从高斯函数。
// 3x3高斯滤波核 (sigma=1.0)
[1/16, 2/16, 1/16]
[2/16, 4/16, 2/16]
[1/16, 2/16, 1/16]
我个人习惯用高斯滤波来做轻度去噪。它保留了更多的边缘细节,因为中心像素的贡献更大。但要注意,sigma值越大,平滑效果越强,边缘保留能力也越弱。
4.1.3 中值滤波
中值滤波的思路完全不同。它把窗口内的像素排序,取中间值作为输出。这招对付椒盐噪声特别管用。
我曾经在一个安防摄像头项目里,传感器因为温度过高产生了大量椒盐噪声。均值滤波和高斯滤波都试了,效果很差——噪声点被扩散成一片灰斑。换成中值滤波,3x3窗口一跑,噪声全没了,边缘还特别清晰。
- 均值滤波:去噪能力一般,边缘保留差,计算量最小
- 高斯滤波:去噪能力中等,边缘保留较好,计算量略高
- 中值滤波:去噪能力强(尤其椒盐噪声),边缘保留最好,但需要排序,硬件开销大
4.2 频域滤波:换个角度看问题
空域滤波是在像素层面操作,频域滤波则是把图像变换到频率空间。为什么要这么做?因为噪声和图像细节在频率域里分得更开。
图像的低频部分对应平滑区域,高频部分对应边缘和纹理。而噪声,尤其是高斯噪声,通常分布在高频区域。所以,我们可以在频域里把高频成分“切掉”或“衰减”,再变换回空域,就得到了去噪后的图像。
4.2.1 小波变换去噪
小波变换把图像分解成不同尺度的子带:低频近似分量、水平细节、垂直细节、对角细节。噪声主要分布在细节子带中。
小波去噪的流程一般是:
- 对图像做小波分解,得到多层子带
- 对细节子带做阈值处理(软阈值或硬阈值)
- 重构图像
我记得在手机ISP项目中,我们尝试用小波去噪来替代空域滤波。效果确实好,但问题是——硬件实现太复杂了。小波变换需要多级流水线,还要处理边界延拓,面积和功耗都吃不消。最后只在高端旗舰机上用了,中低端机型还是老老实实用空域滤波。
4.2.2 DCT变换去噪
DCT(离散余弦变换)大家应该不陌生,JPEG压缩用的就是它。DCT把图像块(通常是8x8)变换到频域,得到DC系数和AC系数。
去噪的思路很简单:AC系数代表高频细节,噪声也在这里。我们可以对AC系数做阈值处理,或者直接丢弃较小的AC系数。
// DCT去噪伪代码
for each 8x8 block:
dct_block = DCT(block)
for each coefficient in dct_block:
if abs(coefficient) < threshold:
coefficient = 0
block = IDCT(dct_block)
DCT去噪在硬件上比小波友好得多。8x8块大小固定,计算规律性强,适合用SIMD或专用加速器。我在一个视频降噪项目里用过DCT去噪,配合运动补偿,效果相当不错。
4.3 空域 vs 频域:怎么选?
这个问题没有标准答案,我根据自己的经验给个参考:
| 维度 | 空域滤波 | 频域滤波 |
|---|---|---|
| 去噪效果 | 一般,容易丢失细节 | 较好,可针对频率分量处理 |
| 边缘保留 | 中值滤波好,均值/高斯差 | 较好(小波优于DCT) |
| 硬件开销 | 低,适合流水线 | 高,需要变换模块和行缓存 |
| 实时性 | 高,延迟低 | 中等,有块处理延迟 |
| 适用场景 | 实时ISP、低功耗设备 | 离线处理、高端成像 |
4.4 本章小结
去噪算法的基础,说白了就是空域和频域这两条路。空域滤波简单直接,适合硬件;频域滤波效果更好,但代价也更高。我个人在项目中,80%的场景用空域滤波就能搞定,剩下20%才需要频域出手。
嗯,这里要提醒大家:不要为了追求技术上的“高级”而盲目选择复杂算法。去噪的本质是“在去噪和保边之间找平衡”,这个平衡点,需要你根据具体的传感器噪声模型、应用场景和硬件资源来定。