ARTICLE · INTELLIGENCE

战地情报 · 详情页

来自尧图项目组的一线实战观察与深度解析

森林火灾目标检测数据集设计与部署实践:烟火识别工程化指南

森林火灾目标检测数据集设计与部署实践:烟火识别工程化指南

森林火灾这个事,一旦蔓延开,就不是人力能快速压住的了。真正有效的窗口期往往只有起火后的几分钟到十几分钟,所以这几年从林场监控、铁塔摄像头到无人机巡航,大家都在做一件事:尽早发现烟火信号。而实现这个目标的核心技术手段,就是目标检测模型。模型要落地,数据就是地基,数据质量直接决定模型在真实场景里敢不敢用。我最近整理完“第5期 森林火灾目标检测数据集”,这一版重点补了远距离小目标、夜间红外、遮挡目标三类难样本,同时对前几期标注边界模糊的问题做了系统性修正。这篇就把这套数据集的完整设计思路、标注规范、模型训练评估结果以及实际部署中踩过的坑一次写清楚,给正在做烟火识别工程化的朋友一个可参考的落地样本。

1. 数据集的整体设计与定位

1.1 为什么单独做一个森林火灾目标检测数据集

很多入门的人会想,直接用开源的通用目标检测数据集不就行了,比如COCO、VOC,里面也有fire、smoke类别。但实际用来做森林火灾监测就会碰壁:通用数据集里的烟火样本大多数是近距离、大目标、高清晰度的火灾照片,而真实森林监控画面里,火苗可能只有十几个像素,烟雾是半透明的、和云朵背景混在一起,前景还有大量树枝干扰。这种分布差异直接导致模型在通用数据集上训练后,拿到林场实测,误报率极高、召回率极低,根本没法用。

所以森林火灾目标检测数据集的核心价值,不是“有没有烟火”,而是“模拟真实监控条件”。第5期数据集的定位特别明确:服务于森林防火预警系统中的早期烟火检测,覆盖监控摄像头、无人机航拍、铁塔高点三种常见部署方式,场景距离从近景(几十米)到远景(数公里)都有分布。数据集中远景样本占比超过60%,小目标样本占总标注框数的45%以上,目的就是把模型训练的注意力和真实部署拉齐。

1.2 数据构成与场景覆盖

第5期数据集总计包含约1.2万张标注图像,其中正样本(含烟或火)约8000张,负样本(无烟火干扰图像)约4000张。负样本不是凑数的,它们是从林场监控录像、户外风景图中专门挑选的“近似烟火”干扰场景,比如白云、晨雾、炊烟、逆光光晕、白色建筑,这些是模型在实际使用中最容易误判的对象。

场景覆盖是这一版的另一个重点。所有图像按拍摄环境做了分层标注元信息(记录在文件命名和配套JSON中,不强制写入模型训练标签),维度包括:

  • 拍摄视角:高位固定监控、无人机俯拍、地面平视
  • 天气条件:晴天、阴天、雨雾、夜间
  • 光照方向:顺光、逆光、侧光
  • 地形背景:林缘、山谷、草坡、岩石裸地
  • 目标距离:近景(目标占图高度1/3以上)、中景(1/10~1/3)、远景(小于1/10)

这套元信息非常关键。训练的时候你可以直接用全量数据,但如果某个部署点位是无人机视角为主、夜间场景居多,可以用元信息筛出子集做二次微调,效果比盲目堆全量数据好很多。

1.3 第5期迭代了什么

第5期不是简单的扩充数量,而是针对性迭代。前四期我踩过几个明显问题:一是小目标标注不完整,很多只有几个像素的烟点漏标,等于变相告诉模型“小目标不重要”;二是夜间可见光图像里烟火特征太弱,标注存在大量模糊框;三是红外图像完全没有覆盖。

这一期做了三件核心调整。第一,所有标注经过两轮独立标注加一轮交叉复核,小目标漏标率从之前的约15%压到了3%以内。第二,新增约2000张红外图像样本,覆盖夜间林区监控和高空热成像两种常见场景。第三,补充了被树干、山体局部遮挡的烟火样本约1200张,这类样本在真实火情中非常常见,但开源的火灾数据集几乎不关注。

2. 目标类别体系与标注规范

2.1 类别怎么定:火焰与烟雾

类别的定义直接影响模型的可用性。第5期数据集只设两个目标类别:Fire(火焰)和Smoke(烟雾)。

为什么不把烟和火合成一个类?很多第一次做烟火识别的人会这么想,反正报警就是有事。但实际不是这样。森林火灾早期,往往先见烟后见火,甚至在林下阴燃阶段只有烟没有火。如果把烟和火合为一类,模型学到的特征就会被两种形态完全不同、尺度差异很大的目标拉扯,导致“有火没烟不好检、有烟没火也不好检”。分开标注后,你可以做二级决策:检测到Fire直接高优先级报警,检测到Smoke降级为预警,人工复核画面。这在工程上更合理。

另外,红外图像中火焰特征和可见光差别很大,烟雾在红外里反而可能不可见。所以类别体系在红外子集中简化为只看Fire,不标Smoke。标注规范里把这个差异写清楚,避免标注员在红外图里硬找烟雾轮廓,标出一堆无效框。

2.2 边界框标注的关键规则

标注规则是数据集质量的生命线。第5期的边界框规则有几条硬性规定,我结合之前几期的教训总结如下:

  • 火焰标注框需要完整包住发光区域,包括火焰上方的光晕,但不能随意扩大。光晕和火焰本体在视觉上连续,模型训练时需要学“发光即火”,框得太紧会漏学习光晕特征,框太松全是背景噪声。
  • 烟雾标注框只包住不透明或半透明的烟雾主体区域,外沿的稀薄扩散部分不标记。原因很简单,烟雾边缘是渐变的,强行把半透明部分画进框里,会让模型对边界极度困惑,直接表现为训练loss不降。
  • 烟和火同时出现在画面时,分别标注两个框。但如果火焰被浓烟包裹,肉眼看不到下方火体边界,只标Smoke,不标Fire。这是为了控制标注的主观漂移。
  • 目标高度小于8像素不标注。8像素以下的目标在1080p画面里人眼都很难确认,硬标只会制造噪声。

最后一条8像素阈值是几次实验后定下来的。低于这个尺寸的烟点,标注员之间的一致性很差,同一张图不同人标出来的位置能差三四倍。与其让模型学一个抖动极大的标签,不如先忽略掉。后续可以靠图像切片放大来处理这种极微小目标。

2.3 复杂场景的特殊处理

森林场景里有两类目标比较难处理:被遮挡的烟火和透明烟柱。

被遮挡的烟火标注时,只画可见部分,不允许推测遮挡区域后脑补完整轮廓。比如一团火苗被前面的树枝挡住了一半,就框露出的一半即可。这是因为目标检测的标注必须与模型看到的信息一致,模型看不到的部分不应该参与训练监督。如果你脑补完整框,相当于告诉模型“那个位置有火”,但图像特征里没有对应信息,等于制造矛盾样本。

透明烟柱的处理更讲究。低矮植被间的薄烟、清晨山谷里的轻雾状烟,肉眼能看见,但灰度值和背景差异极小。这类样本我保留,但会在配套的标注文件中打上hard标记。训练时建议把hard样本单独作为难例微调集,不要一开始就混入主训练集。我实测下来,把hard样本先放一边、等模型AP稳定后再加入,比一开始混合训练最终mAP能提升3~5个点。

3. 数据划分思路与模型训练评估

3.1 训练集/验证集/测试集怎么划

数据划分看起来简单,实际很容易踩坑。森林火灾数据大多来自连续视频抽帧,如果按普通随机划分,同一个视频片段的前后帧会同时出现在训练集和验证集中。这样模型在验证时相当于“开卷考试”,表面指标很好,一换全新场景立刻崩溃。

第5期采用按场景分组的划分方式:先把所有图像按视频源聚类,再把整个簇的内容整体划分到训练集、验证集和测试集。其中训练集约9600张,验证集约1200张,测试集约1200张。测试集单独留出800张为“跨场景测试集”,里面全部是训练中完全没见过的林区点位图像。我建议你拿到任何数据集的第一次评估,都优先看跨场景测试集指标,那才是部署到新点位时的真实预期。

3.2 基线模型与关键参数

我拿第5期数据分别跑了几个常见模型,给大家一组可直接对比的基线数据:

模型输入分辨率mAP50mAP50-95单帧推理耗时(GPU)
YOLOv8s640x6400.8720.531约3ms
YOLOv8m640x6400.8910.568约6ms
YOLOv8x640x6400.9030.583约12ms
RT-DETR-L640x6400.8840.554约9ms

这组结果是默认参数下跑出来的,没有做精细调优。可以看到,在mAP50维度各模型差距不大,都在0.87以上,但mAP50-95差距明显,说明复杂场景下的框质量差异还是有的,模型上限更高。

训练参数方面,我推荐一组比较稳的起点配置:imgsz=640、batch=32、epochs=200、optimizer=AdamW、lr=0.001、weight_decay=0.0005。数据增强我建议初始阶段只开mosaic=0.5、fliplr=0.5、轻微色彩扰动,不要一上来就hsv强化和旋转90度。烟火目标对颜色和纹理变化比较敏感,增强过猛会让早期训练发散,后面还得回头调,得不偿失。

3.3 评估指标怎么看

森林火灾检测里,mAP只是参考,业务上更该关注的是召回率和误报率。原因很简单:漏报一次火情代价极高,误报一次最多多跑一趟人工复核。

根据第5期数据的测试结果,YOLOv8m在置信度阈值0.25下,Fire类别召回率0.93,Smoke类别召回率0.88,整体误报率约3.7%。这个误报率数字看着不高,但换算到24小时持续运行的监控系统就麻烦了。一套100路的监控平台如果每路每10分钟一次误报,每分钟就有10次假警推送,很快值班人员就会把系统静音,系统等同报废。所以阈值设置、报警策略、置信度校准,跟模型本身一样需要认真调。

Smoke类别召回率偏低是普遍现象,根源是烟雾和天空、云层、晨雾在纹理特征上有大量重叠。第5期在基础训练之后,额外用hard样本做了两轮微调,才把Smoke召回率从0.82提到0.88。

4. 模型部署实战:误报来源与排除策略

4.1 最常见的误报源头

模型到了真正部署点位,最大的挑战不是漏检,而是误报高到你不敢信。

林区监控里最典型的误报源是云和移动光影。白天一团白云从山脊飘过,如果云的灰度分布恰好和烟雾相似,模型很容易给出高置信度输出。尤其在高空俯拍的场景里,镜头朝下时云不在视野里,但镜头平视远方时,云层几乎就是“天空中的白块”,跟远处灰白的烟柱在特征空间非常接近。要压住这一类误报,光靠换模型不够,还得在数据里刻意加重云图样本的比例。第5期负样本里云图占了一大块,就是为了逼模型学会区分“贴地的烟”和“天上的云”。

另一个高频误报源是炊烟和灰尘。林场周边有村落、有施工道路,炊烟从屋顶烟囱升起时,形态、颜色和森林火灾烟差不多,模型很难区分。这里我的经验是不要硬刚模型,要在策略层解耦:针对固定点位监控,用区域屏蔽把已知的生活区、道路划为低优先级区域;针对空中飞行的无人机巡检,结合飞行动线和已知村落坐标过滤报警。数据能解决一部分问题,但业务规则必须配合上。

4.2 漏检痛点:逆光、遮挡、极远小目标

漏检最严重的情况集中在这几类:

逆光条件下的烟。太阳在目标背后时,烟雾边缘被强光吞没,整片画面灰蒙蒙一片,人眼都看得费劲,模型更难。针对这个问题,可以在部署端对逆光时段单独做图像增强,例如限制对比度自适应直方图均衡化(CLAHE),再进入检测模型。我实际测试过,逆光样本单独走增强分支,Smoke召回率能提升6~8个百分点。

被树干遮挡的火苗。前面说过标注时只框可见部分,这会导致模型对局部特征的学习要求更高。解决思路是增加这类遮挡样本,并且推理时对图像做多尺度预测,让模型既能看到全局上下文也能看到局部细节。第5期专门加了1200张遮挡样本,就是为了逼模型从“透过树枝的橙黄色光斑”识别出火的存在。

极远距离小目标。单靠整帧图像上的模型推理,8像素以下的目标根本检测不到。工程上有两个常用补救方案。第一是图像切片,把原图切成2x2或者4x4的子图,分别送入模型再合并结果,相当于变相提高输入分辨率。第二是多尺度融合,在模型输入侧同时保留全图和局部放大图两路,全程两路帧率可以不同,小目标漏检率下降最明显。

4.3 误重复报警与时间稳定性

单帧检测模型直接在视频流里用,会带来一个容易被忽视的问题:目标一帧出现、一帧消失,报警系统被反复触发,值班员一小时内收到上百条相同的火警。排除这个问题不在于模型,而在于时序后处理。

我的做法是滑动窗口投票:连续N帧中,至少M帧检测到目标且位置重叠度高于阈值,才触发报警。N取10~20,M取N的一半以上。这套最简单的时间滤波,可以砍掉超过90%的闪烁误报,代价是延迟增加几秒。对林火预警来说,几秒延迟完全可接受,换来的是没人会把报警静音。

5. 数据集本身的局限与后续扩展方向

5.1 数据集的短板

虽然第5期做了不少迭代,但必须承认它还有明显局限。最大短板是正样本的“真实大火”图像不足。真实的森林火灾发展中期,火线长、烟雾浓密、燃烧范围大,这种画面难以获取,数据集中占比低。但模型的部署价值恰恰体现在初期和中期都能可靠告警。如果训练数据里中期大火样本少了,模型可能在火势变大后反而失稳。所以拿到数据集后,建议自己再用公开渠道补充大火场景样本做二次微调,哪怕只有几百张也很有帮助。

第二个短板是检测灵敏度与算力预算的矛盾。数据集里大量小目标和红外样本,意味着高精度推理需要更大的输入分辨率和更高的算力。在边缘设备上跑,算力有限,分辨率受限,模型性能会明显下降。这不是数据集本身能解决的,但在选型时要注意平衡。

5.2 标注质量的自查方法

文本标注界面容易让人产生信任错觉,事实上标注错误极其常见。分布式训练数据时,我强烈建议至少抽查5%的图像做人工复核,重点看三类错误:小目标漏标、框偏移大、类别混淆(火标成烟)。如果你想自动化一点,可以用模型对训练集做一次预测,把预测分数高但无标注框的区域全部筛出来复查,这些区域极可能是漏标。这个方法我每次都用,每次都能找出几十处硬错误。

5.3 后续扩展:从单帧检测到多帧联动

数据集本身是静止图像标注,但真实部署环境是视频流。如果后续有条件,我建议把这一套数据集扩展到视频时序领域。具体做法是把连续帧抽出来,构成带时间戳的片段,标注出目标首次出现帧、目标大小变化、火势蔓延方向等信息。有了这类数据,模型就能从单帧检测升级为时序预测,将来可以做火势蔓延速度估计、烟羽走向预判,这些对调度扑救力量非常有价值。

基于第5期数据集,下一步我打算做两件事:一是给推理端接一个轻量级时序投票模块,实测一下在不同延时档位下的综合报警准确率;二是继续扩采夜间红外和无人机高空俯拍样本,把Smoke类在远距离弱纹理场景里的召回率再往上提。做数据集成这件事,永远没有做完的那一天,每补一批真实场景数据,模型在野外就少一分赌运气的成分。

RELATED READING

延伸阅读

更多一线实战笔记与深度复盘,助您持续精进