3. 图像预处理实战:图像滤波、边缘检测与形态学操作
说实话,很多刚入行的同学觉得图像预处理就是「调参游戏」。高斯核多大?Canny阈值设多少?随便调调就行。
但我得说,这个想法很危险。我在实际项目中吃过不少亏——有一次在高速场景下,就因为滤波参数没选好,把远处的行人轮廓给抹掉了,差点酿成大错。所以今天这一讲,咱们把预处理这块硬骨头啃透。
3.1 图像滤波:去噪是第一步
传感器采集的图像,说白了就是一堆离散的像素点。受光照、传感器噪声影响,这些点总会有「毛刺」。滤波就是把这些毛刺磨平。
3.1.1 高斯滤波
高斯滤波是我最常用的。它的核心思想很简单:每个像素的值,由它周围像素的加权平均决定。权重符合高斯分布——离中心越近,权重越大。
为什么用高斯?因为自然界的噪声大多服从高斯分布。用高斯滤波去高斯噪声,这叫「对症下药」。
import cv2
import numpy as np
img = cv2.imread('road.jpg')
# 高斯滤波,核大小5x5,标准差1.5
gaussian = cv2.GaussianBlur(img, (5, 5), 1.5)
3.1.2 中值滤波
中值滤波就更有意思了。它不是算平均,而是取邻域内所有像素的「中位数」。
你想想看,如果图像里有椒盐噪声(黑白点),用高斯滤波会怎样?噪声点会被「平均」到周围,虽然变淡了,但还是存在。但中值滤波直接把这个异常点替换成中位数,干净利落。
# 中值滤波,核大小3
median = cv2.medianBlur(img, 3)
3.2 边缘检测:Canny算子详解
边缘检测是视觉感知的基石。车道线、行人轮廓、车辆边界——这些都需要边缘信息。Canny算子是目前最经典的方案,没有之一。
3.2.1 Canny的四个步骤
- 高斯滤波去噪——先磨平毛刺
- 计算梯度幅值和方向——用Sobel算子算x和y方向的梯度
- 非极大值抑制——只保留梯度方向上的局部最大值
- 双阈值检测——高阈值确定强边缘,低阈值连接弱边缘
嗯,这里要注意第三步。非极大值抑制说白了就是「瘦身」——把边缘变细,只保留最亮的那条线。否则你得到的边缘会像毛笔画的一样粗。
# Canny边缘检测
edges = cv2.Canny(img, 50, 150)
# 参数:低阈值50,高阈值150
阈值怎么调?我一般用「2:1」或「3:1」的比例。比如低阈值50,高阈值150。高阈值太高会丢失边缘,太低会引入大量噪声。
我的习惯做法:先用低阈值看整体边缘,再逐步提高高阈值,直到噪声消失。
3.3 形态学操作:让边缘更干净
做完边缘检测,你会发现图像里有很多「碎渣」——孤立的小点、断裂的线条。形态学操作就是用来处理这些问题的。
3.3.1 腐蚀与膨胀
这两个操作是基础。腐蚀是「收缩」,膨胀是「扩张」。
- 腐蚀:消除小白点,让物体边界向内收缩
- 膨胀:填补小空洞,让物体边界向外扩张
kernel = np.ones((3,3), np.uint8)
erosion = cv2.erode(img, kernel, iterations=1)
dilation = cv2.dilate(img, kernel, iterations=1)
3.3.2 开运算与闭运算
开运算 = 先腐蚀后膨胀。用来消除小噪点,同时保持物体大小不变。
闭运算 = 先膨胀后腐蚀。用来填补物体内部的小空洞。
# 开运算
opening = cv2.morphologyEx(img, cv2.MORPH_OPEN, kernel)
# 闭运算
closing = cv2.morphologyEx(img, cv2.MORPH_CLOSE, kernel)
3.4 实战组合拳
在实际的自动驾驶感知系统中,这些操作通常是组合使用的。我分享一个常用的预处理流水线:
- 高斯滤波去噪(核5x5,sigma=1.5)
- Canny边缘检测(阈值50/150)
- 形态学闭运算(核3x3,填补边缘断裂)
- 形态学开运算(核3x3,去除孤立噪点)
def preprocess_pipeline(img):
# 1. 高斯滤波
blurred = cv2.GaussianBlur(img, (5, 5), 1.5)
# 2. Canny边缘检测
edges = cv2.Canny(blurred, 50, 150)
# 3. 闭运算
kernel = np.ones((3,3), np.uint8)
closed = cv2.morphologyEx(edges, cv2.MORPH_CLOSE, kernel)
# 4. 开运算
cleaned = cv2.morphologyEx(closed, cv2.MORPH_OPEN, kernel)
return cleaned
好了,这一讲的内容就到这里。图像预处理看似基础,但它是整个感知系统的「地基」。地基没打好,后面的目标检测、跟踪都会出问题。下一讲我们会进入更核心的目标检测环节,到时候你就知道预处理做得好有多重要了。