1. 雾霾环境下的道路目标检测挑战
在智能交通和自动驾驶领域,道路目标检测是最基础也最关键的环节。但当我们把检测场景放到雾霾天气下时,问题就变得复杂起来。我做过不少实际项目,最头疼的就是遇到能见度不足100米的雾霾天——传统检测算法在这种环境下准确率能掉到50%以下。
雾霾对图像质量的影响主要体现在三个方面:一是大气散射导致图像整体对比度下降,就像给镜头蒙了一层纱;二是光照不均造成局部过曝或欠曝;三是色彩失真,特别是远处物体几乎与背景融为一体。去年在河北某地的实测数据显示,普通YOLOv5模型在PM2.5超过300时的漏检率高达42%,这对自动驾驶系统来说绝对是灾难性的。
2. 算法整体设计思路
2.1 双阶段处理架构
经过多次实地测试,我最终采用了"预处理+检测"的双阶段架构。这个方案最大的优势是既能保留YOLOv5的实时性,又能针对性解决雾霾干扰。第一阶段使用改进的暗通道先验算法进行图像增强,第二阶段才是目标检测。
这里有个关键设计取舍:为什么不直接用端到端网络?实测发现,将去雾和检测分开处理,在保持95%以上准确率的情况下,推理速度比端到端方案快23%。这对于需要实时响应的车载系统至关重要。
2.2 图像增强模块优化
2.2.1 改进的暗通道先验算法
传统暗通道算法在处理浓雾图像时容易产生光晕效应。我的改进主要在三个方面:
- 采用引导滤波替代软抠图,速度提升15倍
- 自适应大气光估计,避免固定窗口导致的估计偏差
- 引入透射率修正因子,公式如下:
t(x) = 1 - ω * min(min(I^c(y)/A^c))其中ω取值0.65-0.85效果最佳,需要根据雾浓度动态调整。实测这个改进使PSNR指标平均提高了2.3dB。
2.2.2 多尺度融合增强
单一尺度的增强会丢失细节,我采用了金字塔分解策略:
- 对原图进行高斯金字塔分解(3层)
- 对不同层级分别进行增强处理
- 使用拉普拉斯金字塔重构
这种方法特别适合处理远近景混合的交通场景,远处车牌等小目标的清晰度提升明显。
3. YOLOv5模型专项优化
3.1 数据集的特殊处理
3.1.1 雾霾数据合成
收集真实雾霾数据成本太高,我使用以下方法合成训练集:
- 基于NYU Depth数据集生成深度图
- 应用大气散射模型:
I(x) = J(x)t(x) + A(1-t(x)) - 添加噪声模拟真实传感器噪声
关键是要控制雾浓度梯度,我开发了一个参数化合成工具,可以精确控制PM2.5在50-500μg/m³范围内的合成效果。
3.1.2 困难样本挖掘
针对雾霾场景的特殊性,我增加了三类困难样本:
- 半遮挡车辆(被雾部分遮挡)
- 低对比度行人(与背景相似)
- 远处小目标(小于32×32像素)
这些样本要占训练集的至少30%,否则模型在真实场景表现会大幅下降。
3.2 网络结构改进
3.2.1 注意力机制引入
在YOLOv5的Backbone末端添加CBAM模块:
class CBAM(nn.Module): def __init__(self, c): super().__init__() self.channel_attention = nn.Sequential( nn.AdaptiveAvgPool2d(1), nn.Conv2d(c, c//8, 1), nn.ReLU(), nn.Conv2d(c//8, c, 1), nn.Sigmoid()) self.spatial_attention = nn.Sequential( nn.Conv2d(2, 1, 7, padding=3), nn.Sigmoid())这个改进使小目标检测AP提升了4.7%。
3.2.2 特征融合优化
将原来的PANet结构改进为BiFPN:
- 增加跨尺度连接
- 引入可学习的特征权重
- 使用深度可分离卷积降低计算量
实测在保持速度不变的情况下,mAP提升2.1%。
4. 工程实现关键细节
4.1 部署优化技巧
4.1.1 TensorRT加速
在Jetson Xavier上部署时,这几个优化点很关键:
- 使用FP16精度,速度提升3倍
- 设置opt_profile_num=3以适应不同雾浓度
- 启用sparse convolution加速
最终在1080p输入下能达到35FPS,完全满足实时性要求。
4.1.2 内存优化
处理高分辨率图像时容易OOM,我的解决方案:
- 使用动态batch size
- 将图像增强模块移到GPU上执行
- 采用分块处理策略
这样在8GB显存的设备上也能处理4K输入。
4.2 实际应用中的调参经验
4.2.1 动态参数调整
雾霾浓度是动态变化的,我开发了一个浓度估计模块:
- 基于暗通道强度估计浓度等级
- 根据浓度自动调整:
- 图像增强参数
- 检测阈值
- NMS参数
这个设计使系统在雾浓度变化时也能保持稳定表现。
4.2.2 后处理优化
标准NMS在雾天容易误合并,改用Soft-NMS:
def soft_nms(dets, sigma=0.5, thresh=0.3): keep = [] while dets: max_idx = np.argmax(dets[:, 4]) keep.append(max_idx) ious = bbox_iou(dets[max_idx], dets) dets[:, 4] *= np.exp(-(ious**2)/sigma) dets = dets[dets[:, 4] > thresh] return keep这样处理重叠目标时更符合雾天的实际情况。
5. 实测效果与对比分析
5.1 定量评估
在自建的FoggyCity数据集上测试结果:
| 方法 | mAP@0.5 | 推理时间(ms) | 内存占用(MB) |
|---|---|---|---|
| 原始YOLOv5 | 58.3% | 28 | 1200 |
| 本文方法 | 82.7% | 35 | 1450 |
| 其他SOTA | 79.5% | 52 | 2100 |
特别是在浓雾场景(PM2.5>300)下,行人检测AP达到76.3%,比基准方法高31.5%。
5.2 典型场景分析
5.2.1 远距离小目标
在300米外的车辆检测场景:
- 原始方法漏检率:63%
- 本方法漏检率:22% 关键改进在于多尺度特征融合和注意力机制。
5.2.2 高密度遮挡
早高峰拥堵路段:
- 原始方法误检率:18%
- 本方法误检率:7.5% Soft-NMS和困难样本挖掘起了主要作用。
6. 常见问题与解决方案
6.1 图像增强过度
症状:增强后图像出现伪影或噪声放大 解决方法:
- 限制透射率下限(t_min=0.1)
- 添加后处理降噪
- 动态调整ω参数
6.2 雨天误识别
雾霾和雨天的光学特性不同,容易误判:
- 增加雨天数据增强
- 开发天气分类模块
- 使用不同的增强参数组
6.3 边缘设备部署
在树莓派等设备上的优化技巧:
- 量化到INT8
- 裁剪非必要算子
- 使用Tiny版本的YOLOv5
- 将增强模块改为CPU执行
7. 实际项目经验分享
在山西某智慧高速项目中,我们遇到了几个教科书上没写的坑:
- 隧道出入口的亮度突变会导致增强算法失效,最后通过添加光照估计模块解决
- 冬季雾霾常伴随雪花,需要在数据增强时加入雪花噪声
- 大货车卷起的尘土会造成短暂干扰,开发了基于时序的滤波算法
另一个重要发现是:不同地区的雾霾光学特性其实有差异。比如北方雾霾更多是干燥颗粒物,南方则是湿润气溶胶,这对透射率模型的影响能达到15%左右。最好的办法是在目标地区采集本地数据做微调。