车载视觉感知真正难的地方,从来不是公开数据集上的分数,而是极端光照、恶劣天气和罕见目标这些极限条件下的稳定性。前阵子做道路实测数据复盘,翻到一段印象很深的视频:黄昏时段,车辆刚从隧道口驶出,阳光斜射进前向摄像头,画面高光区一片惨白,而就在那片惨白边缘,一个深色轮廓的障碍物几乎和阴影融为一体。检测框在这一帧丢掉目标,下一帧又重新抓到,车厢里所有人都在等系统是否会在最后一刻给出预警。类似的场景做车载感知的同行都不陌生——隧道口的光照陡变、暴雨中模糊的前方视野、路上突然出现的异形装载车辆,这些才是算法从实验室走向量产时真正要过的关。
这篇文章就围绕检测算法在这三类极限条件下的演进,把硬件底座的限制、图像增强策略、数据与模型两侧的工程化解法,以及测试评估方面的一些经验系统梳理一遍。适合正在做车载感知算法开发、数据闭环或测试验证的工程师,也适合想了解自动驾驶感知能力边界的学生和研究者。
1. 极端光照:成像物理底座的硬约束
1.1 动态范围与曝光:为什么摄像头会"选择性失明"
任何做过车载摄像头选型或者图像调试的人,都会反复碰到同一个矛盾:人眼觉得清晰可见的路口,摄像头拍出来一片漆黑;人眼能应付的逆光场景,摄像头拍出来高光区细节全部丢失。这不是算法不够先进,而是传感器物理层面的动态范围限制。
动态范围说的是同一个画面里,一个像素能区分的最亮区域和最暗区域之间的比例。普通车载CMOS传感器的动态范围大致在60到75dB,而真实户外场景从隧道内的暗部到隧道外的直射阳光,宽度可以轻松超过120dB。多出来的那部分亮度信息只能被丢弃。人眼的视网膜动态范围其实也只有90到105dB左右,但人眼有瞳孔、虹膜和局部适应机制,会不断"重新曝光",所以主观感受上人眼在大部分场景里都能看清。摄像头没有这套机制,进光量由固定的快门和增益决定,强光区域先在像素里饱和溢出,暗部区域则被读出噪声淹没。
这里有一个容易被忽略的细节:高光饱和带来的问题不只是"画面刺眼",而是目标和背景融合在一起。太阳直射下的白色车身、逆光里的深色行人、夜间大灯旁边的路缘,都会因为局部过曝或欠曝而丢失边缘信息。目标检测网络无论结构用得多强,输入这一层已经失去了可分性,后续的卷积网络能做的,只能是在残缺信息上做猜测。
所以做感知算法的第一课不是调模型,而是理解传感器。我印象很深的一次排查是:一个夜间版本召回率始终不达标,反复调输入分辨率、调anchor策略都没用,最后回到原始图像一看,暗部的噪声已经直接把远处行人的轮廓淹没了,压缩和降噪又进一步抹掉了微弱对比度。问题的根在成像链路,根本不在检测网络。
1.2 高频失效场景:隧道口、低角度太阳、夜间眩光
在量产数据里,极端光照导致的失效并不是均匀分布的。从实车数据的统计来看,高频翻车的场景高度集中,下面这三个占了绝大多数。
第一个是隧道口。从隧道内几百勒克斯到隧道外几万勒克斯,亮度跳变发生在极短的距离内,再加上隧道照明角度和出口天空构成的中央高亮、四周偏暗的光照分布,画面亮度极不均匀。检测模型在这个区域的误检率通常比正常开放道路高一个量级。最危险的是出口内侧恰好停着一辆故障车,系统需要同时处理高光下的低对比度和连续的曝光震荡。如果ISP的自动曝光收敛不够快,接下来的几十帧画面都处于过曝状态,检测就全线崩溃。这个场景几乎不能靠单一模块解决,需要传感器、ISP和检测模型协同调整。
第二个是低角度太阳光,尤其是日出日落时段。太阳直射镜头会形成强烈的眩光和镜头内部反射造成的光斑、鬼影;低角度的光还在地面上拉出长条阴影和定向反射,车道线、行人轮廓都发生明显畸变。车道线检测在这个时段偶尔出现的抖动,很多时候不是模型退化,而是路面光照分布与训练数据发生了偏移。采集这类数据时有一个建议:记录太阳方位角和拍摄方向的相对关系,才能系统分析模型对低角度光的敏感性,而不是把问题笼统归结成"黄昏效果差"。
第三个是夜间场景。夜间的困难不是"整体暗",而是动态范围被局部光源撕裂:对向车灯、路灯、LED广告牌、刹车灯,这些高亮光源旁边往往就是需要检测的对象——行人、骑行者、路障。自动曝光会向高亮区域妥协,周围暗区进一步变黑。我在项目统计里发现,夜间召回率下降的根因,大量不是全局感光不足,而是高亮光源周围的局部曝光失败。建议数据平台在记录时不要只标"白天/晚上",把"强逆光""局部高动态对比度""眩光""鬼影"这些光照属性单独存下来,后面排障和训练阶段能省很多功夫。
1.3 图像增强与检测联动:ISP不是"后处理"
成像质量受限,很多人的第一反应是加强图像增强。实际做法比想象中复杂,而且有不少反直觉的坑。
HDR多帧合成是车载摄像头最常用的方案,原理是快速连续拍几帧不同曝光量的图像,再合成一帧高动态范围的图。效果立竿见影,代价却在于运动重影:行人在帧间移动,合成结果里出现轮廓残影,边界框定位直接受影响。有些团队用更短的帧间隔或者运动补偿来缓解,但补偿本身又会引入新的伪影。所以我从不默认"HDR一定会提升检测精度",一旦它改变了图像噪声分布和目标边缘形态,就必须用检测指标去验证,而不是只看主观画质。
局部色调映射(LTM)是另一个常用手段,把过曝区域拉回来、暗部提亮,画面看起来非常"清晰"。但这里有一个反直觉的地方:检测模型训练时适应了固定成像管线的输出分布,LTM改变了局部亮度分布和对比度统计,模型可能在"人眼看着更清楚"的图像上反而表现变差。我做过一个对比实验,夜间城市道路场景下开强LTM后,人眼主观画质明显提升,但模型在路口的误检率上升了——因为LTM把暗部噪声同步放大,模型把噪声纹理当成了边缘特征。
后来我定了一条原则:ISP参数和检测模型必须做联动回归评估,先固定检测模型扫描ISP参数,选出最优配置后再回头训练检测模型,避免主观画质和检测精度脱节。这个阶段的核心总结是:极端光照问题,要从传感器物理边界出发,用ISP工程配合数据分层去管理,而不是指望检测网络单方面兜底。
2. 恶劣天气:物理退化模型与数据驱动策略的博弈
2.1 雨、雾、雪对图像退化的机制差异
恶劣天气里,雾被研究得最多,因为它有一个非常简洁的物理模型:大气散射模型。远处物体的反射光穿过雾层时被吸收和散射掉一部分,雾层本身又把环境光散射进成像路径形成"白布",最终图像是两者的叠加。用公式表示就是 I = J·t + A·(1-t),其中J是原始辐射,t是透射率,A是大气光。距离越远,透射率t越小,画面就越糊、越白。
这个模型解释了为什么雾天检测的置信度普遍偏低:目标的形状信息并没有完全消失,而是对比度被压到极低。一辆深色车出现在浓雾里时,车身纹理和背景的亮度差变得非常小,检测网络能提取的特征响应随之减弱,边界框位置开始抖动,容易把车身的暗部和后方道路的暗色块混为一体。
雨和雪又与雾不同。雨的影响主要有两类:雨滴在单帧里形成高速运动的短线遮挡,雨滴附着在镜头或挡风玻璃上形成弥散光斑与模糊区。单看一帧,雨线可能恰好盖住关键目标;看连续视频,雨线的随机位置又让时序模型难以依赖前后帧的一致性。雪花的干扰更接近随机高亮噪点,夜间车灯照射下,雪花会变成一片密集明亮的噪点云,严重时直接覆盖目标边缘。
这些机制差异说明,不存在一个万能的"天气增强模型"可以同时解决所有问题。有的方案是先检测天气类型、再走不同的处理分支;有的方案是干脆不分天气,用一个统一鲁棒表征来应对。两条路线在不同数据规模下各有胜负,需要在具体的数据分布里验证。为了便于直接对照,我把三种天气的退化机制、影响表现和应对方向整理如下:
| 天气类型 | 主要退化机制 | 对检测的具体影响 | 常用应对方向 |
|---|---|---|---|
| 雾 | 大气散射,全局对比度下降 | 远目标置信度低、边界框抖动 | 散射模型仿真、域适应训练 |
| 雨 | 雨线局部遮挡、镜头水膜弥散 | 目标边缘被切断、时序不一致 | 时序融合、水滴抑制、雨刷联动 |
| 雪 | 高亮随机噪点、夜间散射窗 | 边缘被噪声覆盖、误检上升 | 噪声鲁棒训练、多传感器辅助确认 |
2.2 去雾算法:从物理先验到端到端学习
传统去雾路线的代表是暗通道先验(DCP)。它基于一个统计规律:无雾图像的非天空局部区域,总存在某个颜色通道的值非常低。据此可以估算透射率t,再反推清晰图像。这个方法在图像处理时代是里程碑式的,但落地到车载场景时问题不少:天空区域失效、深色物体本身满足暗通道假设导致透射率被低估、计算开销偏高,而且去雾后容易出现halo伪影。做后处理展示可以,做量化感知系统就不太够用。
深度学习的去雾路线分成两类。一类是在合成雾图上训练端到端去雾网络,直接输出清晰图;另一类更激进,不做传统意义上的"去雾",而是用域适应或风格迁移,让在晴天数据上训练好的检测模型直接吃雾天输入。这里我要强调一个观点:去雾本身不是目标,检测精度才是。在很多实测里,去掉雾得到的"清晰图"并未带来检测收益——去雾网络一旦引入伪纹理或改变色调分布,前端检测网络反而会出现新的错误模式。与其追求完美的去雾模型,不如把雾天数据直接纳入训练分布,让检测网络在原始雾图上自己学习特征。这也是为什么各路数据增强管线里,基于大气散射模型的雾天仿真越来越重要的原因。
2.3 天气仿真与domain gap的工程处理
为什么天气仿真几乎是必选项?因为很难拿到足量且分布合理的真实恶劣天气数据:雾气浓度、高度、光照、场景结构组合起来近乎无穷,浓雾天气下采集车队也没法安全作业。
最简单的一条仿真路径就是套大气散射模型:已知深度图,设定全局雾浓度,生成物理上接近真实的雾图。但实际用下来,均匀雾与真实大气雾在近处目标上差别不大,在远处目标上差别很大。真实雾的空间结构、气流、光照方向都非常不均匀,均匀仿真让远处看起来"假",模型学到的是"远处等于变白"的简单映射,而真实雾中远处的目标往往还带有微弱的颜色与结构信息。这会让模型错误地依赖颜色饱和度来判断距离,反而降低对真实远距离目标的敏感性。
改进方法是把透射率和大气光场都做成空间变化的场,用真实深度数据驱动,叠加多层噪声扰动,让合成雾的空间分布接近真实。更进一步的做法是用神经渲染把真实场景重建后叠加气象条件,能生成非常逼真的雨雪数据,但训练成本高。工程上的折中建议是:合成天气数据作为训练分布的一部分,不能全部替代真实数据。保留少量真实的雾、雨、雪片段用于校准,能显著降低domain gap带来的性能衰减。实测下来,这个"仿真为主、真实兜底"的组合,往往比单一来源的数据更能稳定提升恶劣天气下的检测成绩。
3. 罕见目标:长尾分布下的检测失灵与重建
3.1 为什么罕见目标会让检测器失效
翻看一个典型车载数据集的目标分布,车、行人、骑手占绝对主体,工程机械、动物、三轮农用车、路面散落物这类类别的样本寥寥无几。训练时损失函数被高频类别主导,网络把有限的特征表达能力优先分配给多数类——这不是模型"偷懒",而是优化方向的必然结果,高频类别提供了最充沛的梯度,学习它们收益最高。
这种不均衡带来一个直接表现:罕见类别的召回率远低于高频类别。更隐蔽的表现是,罕见目标常以"高频目标的变体"形式出现。比如装载超长管道或宽大支架的货车,外观上与训练数据里的标准货车差距很大,检测框可能只能框住一半,置信度极低,或者干脆被划到其他类别。还有一类让行人检测器非常头疼的情况:行人蹲下、倒地,推着轮椅、抱着大件物品,姿态和形状发生极端变化,常规模型几乎必然失效。
"罕见"不等于"不重要"。严重事故数据里大量案例恰恰来自罕见场景——横穿高速的动物、掉落的轮胎、误入对向车道的车辆。安全系统最不能漏掉的,恰好是模型最没见过的目标。所以罕见目标问题本质上是安全约束和数据稀缺之间的深刻矛盾。
3.2 数据侧解法:合成、自动标注与难例挖掘
面对罕见目标,大部分团队的直觉是"多采集真实数据"。但对罕见目标来说,被动采集的效率低得可怕:可能跑了几万公里也遇不到几次特殊装载。数据侧必须靠主动打法,通常绕不开三条路径。
第一层是合成数据。用仿真平台批量生成工程机械、事故现场、散落物,配合扫描建模、姿态随机摆放、天气光照组合,一天可以产出上万张带完整标注的图片。难点始终是sim-to-real gap:合成模型的表面过于干净、纹理过于规整,检测模型在真实图上会过度依赖理想边缘。缓解手段包括随机纹理污染、域随机化以及无监督域适应,都需要在训练流程里做精细控制。
第二层是自动化标注与难例挖掘。极端数据的天气、光照、目标类别组合复杂,全量人工标注成本过高。标准做法是:训练一个基础模型对数据进行预检,抽出模型置信度异常(过低或处于不确定区间)和边界框形态异常的样本,进入人工复核,再回流训练集。这个"模型找难例—人工确认—增量训练"的闭环一旦跑顺,罕见目标数据获取效率会有质的变化。
第三层是数据增强层面模拟"罕见属性":对已有目标做遮挡模拟、极端光照扰动、天气退化叠加,逼着模型在局部信息严重缺失的情况下仍保持输出稳定。这里要强调的是,增强不能盲目堆强度,应遵循真实物理规律,比如雨滴的方向性、光照角度和阴影方向的一致性。模型学到一致的物理规律,才会在真实罕见场景中真正见效。
3.3 模型侧演进:从闭集检测到开放集识别
传统检测是"闭集"范式:训练时定义好车辆、行人、骑手等有限类别,推理时只能在既定类别里做选择。真实世界不会按约定出题,当路面突然出现训练集里从未有过的大件散落物,网络很可能把它归类为背景——这是最危险的失效:目标明明存在,系统却判断为"没有异常"。
针对这个问题的研究方向是开放集识别和异常检测。一个朴素的思路是设置一个"未知类/异常类",当输入特征显著偏离训练分布时归入其中,让系统进入"谨慎模式"而不是"忽略模式"。稳健置信度、最大熵损失等思想都在尝试让网络对未知输入更诚实地"表达不确定"。
另一个被反复讨论的方向是视觉-语言预训练模型迁移到车载场景。这类模型在大规模图文配对上学到了丰富的语义概念,对不常见的目标形态有更强的泛化能力。但车载感知有个现实问题:这类模型对微小位置和高精度边框回归不敏感,直接替换检测框架并不现实。我看到更有潜力的组合方式,是用它来做语义层面的提示或故障检测,再与传统的精确定位分支配合。
工程层面的建议是:在安全攸关的车载感知系统里,始终保留一个"语义不确定感知"的输出通道。当置信度分布混乱、多个类别概率接近时,系统主动降低对场景的理解置信度,触发平台降级策略或转向其他传感器确认。宁可让系统说"看不清",也不要让它平静地下结论说"没有异常"。
4. 测试与评估:极限能力的度量困境与工程实践
4.1 条件分层采集:测试集别出"混合污染"
评估极限条件下的感知能力,困难常在算法之外,首先卡在测试集设计。
很多团队的做法,是把数据粗略分成"白天晴天"和"其他"两类,前者训练,后者测试。但"其他"里混着各种不同原因的失效:甲算法在逆光场景好,乙算法在夜间好,平均指标一出来两者打平,什么都学不到。更好的做法是先按条件分层:光照维度区分顺光、逆光、强逆光、隧道口、黄昏、夜间;天气维度区分晴、雾、雨、雪、暴雨;目标维度区分高频、常见长尾、罕见长尾。各层单独统计,出现指标下滑时,可以直接定位是在哪一层掉的分数。
另一个容易被低估的问题是极端条件下标注本身的质量。浓雾里人眼也看不清远处目标,雨刷区域模糊,标注员的判断不可靠。如果测试集标注噪声大,指标的意义就打了折扣。建议统计低能见度样本的标注分歧率,超过一定阈值就纳入复核流程,或者干脆从测试集剔除,避免错误标注干扰版本对比。我见过好几个项目,反复调整模型发现指标不上不下,最后单独排查标注才发现,雾天测试子集里有将近一成目标的边框位置明显有偏差。
4.2 指标设计的陷阱与三套指标
mAP是检测任务最常用的指标,但它对罕见类别并不友好。类别只有几十个样本时,一两个漏检就能让该类别的AP剧烈波动。拿mAP做回归测试,今天提升3个点,明天因为测试集采样变化下降2个点,根本无法支撑稳定决策。
我倾向于在车载感知项目里同时维护三套指标,不揉成一个数字:第一套是高频类别(车辆、行人、道路结构)在正常与恶劣天气下的AP,用来度量"基本盘"是否稳定;第二套是罕见类别在难例样本集上的召回率(可以取Top-N),用来度量"极限能力"是否提升;第三套是场景级误报率和系统综合支持度,比如夜间误刹车率、隧道口虚警率,这些直接关系用户体验与安全。三套指标分开优化、分开记录、分开复盘,每次算法迭代都明确说明"动了哪一块、影响哪一块"。
| 指标 | 度量对象 | 典型用途 | 主要局限 |
|---|---|---|---|
| 高频类别AP | 车辆、行人、道路结构在晴、雨、雾、夜下的精度 | 回归测试的基本盘 | 对罕见类别不敏感 |
| 罕见类别Top-N召回 | 极端场景罕见目标检出率 | 衡量极限能力提升 | 样本少,方差大 |
| 场景级误报率 | 夜间误刹车、隧道口虚警 | 用户体验与安全评估 | 依赖场景触发与采集 |
4.3 影子模式与灰度验证:让线上极限场景成为训练资产
极端条件的发生频率低,"离线测试表现好"不等于"上线后可靠"。这时候影子模式(shadow mode)的思路很有价值:新算法部署在设备上,但只观察不做决策,将预测结果与实车实际表现做比对。遇到光照突变、降雨、罕见目标出现等事件时,自动记录"如果当时由新系统决策,是否会产生差异"的案例。这样能够积累起大量真实的线上极端场景样本。
影子模式有实施细节。首先,触发条件必须独立设计,不能什么都记,否则数据爆炸但有效信息稀疏。我习惯为每种极端条件设置独立阈值,例如画面平均亮度与动态范围变化率、天气分类模型概率、罕见目标出现置信度等,触发后向前和向后各截取一段数据,构成完整事件单元。其次,影子模式得到的数据分布与主动采集的数据不同,只适合做召回率和误报率的趋势监控,不能直接用做离线测试集。影子模式跑一段时间之后,再人工筛选事件进入标注流程,回流训练,形成真正落地的数据飞轮。
在车载感知项目里待久了,我越来越认可一个判断:极限条件下的感知能力,从来不是单一算法的胜利,而是"成像硬件、ISP管线、数据分布、模型结构、决策策略"五个环节共同演进的系统工程结果。单点突破当然能带来阶段性提升,比如更好的HDR合成、更大规模的长尾数据、更稳健的开放集识别,但真正的可靠,来自每一层都能对自己的不确定有清晰的表达,并且系统愿意为此调整行为。
我自己做完这套梳理之后,做的最实际的一步,是把光照、天气、罕见目标从数据里显式分离出来,分维度建立评估基准。等我能清晰说出"这个版本逆光和夜间有提升,浓雾还没解决,罕见工程车辆召回又涨了一点"这句话时,后续算法迭代的方向就已经比大多数无头绪的试错清晰得多。技术演进没有终点,但每一次改进,都应该知道它是在哪个极限坐标里前进了。