☰
外墙裂缝目标检测数据集:6000+张已标注图片,YOLO训练实测经验
2026/10/19 9:37:05 网站建设 项目流程

做建筑外立面检测的同行应该都有体会:裂缝识别这件事,看着简单,真要做成AI检测模型,第一步就被数据卡住了。网上的裂缝数据集大多是柏油路面的裂缝、隧道衬砌的裂缝,真正面向外墙砂浆、涂料、瓷砖表面的样本少,能直接用于目标检测训练并且已经划分好的更少。所以我前前后后花了大量时间整理了一套外墙裂缝目标检测数据集,6000+张图片,全部完成划分和标注,专为目标检测任务准备,拿到手就能开训YOLO、RT-DETR这类模型。

这篇文章不打算讲空泛的概念,直接把这套数据集的内容构成、标注规范、划分逻辑、实际训练效果和踩过的坑一次说清楚。如果你正在做建筑缺陷检测、无人机外墙巡检、房屋安全评估相关的视觉方案,这篇内容应该能帮你省掉不少自己摸索的时间。

1. 外墙裂缝检测的行业痛点:为什么通用数据不够用

1.1 人工巡检模式的效率瓶颈

外墙裂缝检测是建筑外立面安全评估里的高频需求。墙面开裂不仅影响外观,更是潜在的渗水通道,裂缝走向如果和结构受力方向吻合,还可能暗示主体结构存在问题。传统做法靠人:检测人员站在吊篮里或者借助登高车,逐面墙肉眼观察、用裂缝测宽仪量宽度、用记号笔标记端点,一栋20层的住宅楼,光外立面巡检就得半天,遇到弧形立面或者异形造型,时间还要翻倍。高处的细微裂缝肉眼根本看不清,必须凑到跟前才能判断,这也是人工检测漏检率居高不下的直接原因。

无人机巡检和AI识别在这个场景下之所以被越来越多人接受,核心就是把人从重复劳动里解放出来。但AI落地的前提是有数据,而且是有足够场景针对性的数据。这就引出了外墙裂缝检测和通用目标检测的一个核心矛盾:普通的目标检测数据集没法平移到这个领域使用。

1.2 裂缝检测与通用目标检测的本质差异

很多人以为裂缝检测就是一个"找框框"的任务,拿YOLO训练就行。实际差别很大。通用目标检测里的物体,比如行人、车辆,都有相对固定的形态和整齐的轮廓,边界清晰;裂缝是细长、蜿蜒、不规则的线状结构,一个标注框里可能只有5%到15%的像素是真正的裂缝,剩下全是墙面背景。模型要学的是"从复杂纹理背景里识别出线性异常",这和学"识别一条有尾巴四条腿的猫"完全不是一回事。

裂缝的尺度跨度也极大。有的裂缝横跨整面墙,纵向往返上百米;有的只有几厘米长,缩略图里就是几个像素的小点。同一张图里大小目标同时出现,这对检测模型来说是相当苛刻的要求。而且外墙本身带着各种纹理:涂料接茬、面砖缝、泛碱痕迹、雨水流挂,这些在视觉上有时候比真裂缝还像裂缝,模型稍不留意就会把它们当成目标输出。

1.3 现有公开数据集的三个缺口

我前期调研过不少公开的裂缝数据集,筛下来的感受是三句话:数量不够、场景不对、标注不齐。数量上,很多论文使用的小型数据集只有几百张图,做验证可以,做工程落地就样本多样性不足;场景上,道路裂缝数据集占比很高,沥青路面的纹理和水泥砂浆墙面完全是两种视觉风格,迁移到外墙任务上误检率明显偏高;标注上,部分数据集只提供分类标签,没有检测框,还有一些是图像分割标注,想转成检测框还得自己处理坐标,平白多出一堆清洗工作。

基于这些原因,我当时判断:与其东拼西凑,不如自己整理一套针对外墙场景、面向目标检测任务的数据集。这套数据不一定追求数量上的绝对庞大,但要把场景针对性做透,把标注一致性和数据划分严谨性做到位。这也是这篇文章标题里"6000+张、已划分、已标注"这三个关键词背后的真实原因。

2. 数据集内容与构建思路:6000+张图是怎么做到的

2.1 采集场景与设备选择

这套数据集的构建思路,核心是"窄场景、深覆盖":不追求覆盖所有墙面损伤类型,只把外墙裂缝这一个目标做扎实。图片来自多种不同类型的外墙建筑,包括住宅楼外墙(涂料面和面砖面)、办公楼玻璃幕墙周边墙体、厂房水泥墙面、学校建筑外立面等。采集设备以无人机挂载相机为主,配合少量手持相机补充近景细节,拍摄距离控制在2到5米。这个距离很关键:太远了裂缝变成一条虚影,标注框画出来模型也学不到纹理特征;太近了单张图覆盖面积太小,训练出来的模型容易过拟合局部纹理。

采集时还有两个容易被忽略的细节。一是光线方向,侧光照射时裂缝有阴影衬托,在画面里更明显;正光条件下裂缝对比度大幅下降。数据集里两批图片都保留了一部分,避免模型只学会识别"有阴影的裂缝"。二是墙面湿度,雨后墙面局部颜色变深,裂缝周围更容易出现水痕干扰,这类图片也适度采集了一些,用于提升模型在复杂天气条件下的鲁棒性。

2.2 图像预处理与裁剪策略

原始照片尺寸不等,多数是4000x3000左右的大图,直接用原始尺寸训练检测模型并不划算:显存放不下、训练时间拉长、长尾的小裂缝目标在缩放过程中容易被压没。所以我对大图做了滑窗裁剪,切成640x640的图片块,相邻滑窗之间保留约50像素的重叠,尽可能避免裂缝主体刚好被切在两块图边界上导致目标断裂。

裁剪之后进行了一轮筛选,剔除过曝、严重模糊、墙面占比过小、裂缝几乎不可辨的无效样本。这一轮大概淘汰了20%的裁剪图。留下来的图片再按"同一栋楼同一批次"打上分组标识,方便后面做数据划分。现在很多数据集发布者只给文件不交代分组逻辑,导致使用者拿到数据后没办法正确处理数据泄漏问题,这一点我在整理时就提前规避了。

2.3 类别定义与样本分布

标注类别我最终只保留了一个:crack,统一表示外墙裂缝。可能有人问,为什么不拆成横向裂缝、纵向裂缝、斜向裂缝、龟裂?因为裂缝形态是连续的,很多裂缝同时包含水平和倾斜段,强行分类会让标注边界变得模糊,不同标注者之间的主观判断差异会被放大,模型学到的类别界线反而是噪声。一个统一的crack类配合足够的样本量,训练稳定性更高。

全套数据里,含裂缝的正样本图片约5200张,无裂缝的负样本背景图约800张,标注框总数约1.7万个,平均每张正样本约3个框。需要说明的是,部分图片里裂缝会延伸到画面边缘,这种目标我同样正常标注,不做删除处理,因为实际部署时滑窗裁剪的边缘也经常出现半截裂缝,模型必须学会应对这种情况。

2.4 数据增强策略

数据增强方面我没有做激进的操作,只用了轻度翻转、轻微旋转、色调微调、随机裁剪。裂缝识别的核心特征是线状纹理,过度几何增强(比如极端旋转、拉伸)反而会让裂缝形态失真,模型学到的是不真实的形状。负样本比例控制在15%左右,这个比例既能让模型学会拒绝外墙污渍、管线阴影等背景干扰,又不会因为负样本太多导致训练收敛变慢。

3. 标注规范:目标检测任务真正比拼的第一个细节

3.1 标注工具与人员协作

标注工具建议优先选能导出Pascal VOC格式的,比如LabelImg或X-AnyLabeling,操作逻辑简单,团队协作时上手成本低。不管用什么工具,团队内部必须有一份书面标注规范,不然三个标注员能标出三种框:有人喜欢把裂缝连同周围阴影一起框进去,有人只框裂缝主体,模型收到这种不一致的标签,损失函数会被带偏。

规范里至少要写清楚这几件事:什么算一条裂缝,裂缝和污渍怎么区分,裂缝延伸出画面边缘怎么处理,同一裂缝分段标注的规则。我在整理这套数据时,让参与标注的人先各自标注同一批20张图,再逐框对比差异,把所有分歧点全部摆到台面上讨论,最后形成书面规则。这个过程很琐碎,但对后续模型精度的提升作用远超想象。

3.2 边界框界定原则

我标这套数据时定了几条硬性规则。第一,框必须完整包含裂缝主体,允许包含部分背景,但背景占比不能过高,否则模型不知道你到底在学什么。第二,一条裂缝如果横跨大半面墙、长度超过画面边长一半以上,允许拆分成多个框,每个框内的裂缝主体长度和方向基本一致。第三,裂缝和墙面污渍同时出现时,只在裂缝上画框。第四,单个框内如果同时出现两条互不相连的裂缝,必须分开标注,不允许用一个框包揽。

这些规则听起来琐碎,但直接决定标注质量的一致性。细长目标本来就对框的边界敏感,同样一条裂缝,一个标注员框得宽一点,另一个框得紧一点,模型在匹配IoU时就会产生大量困惑。裂缝这类目标的标注质量,比普通物体更依赖规则的明细程度。

3.3 从VOC到COCO/YOLO的转换

标注完成后统一导出Pascal VOC XML,再用脚本转换成COCO JSON和YOLO txt两种格式。转换脚本网上有很多,但有几个细节特别容易出错:XML里的坐标原点是左上角,YOLO格式要求归一化坐标,转换时坐标必须除以图片宽高;类别索引必须从0开始连续编号;COCO的annotations里image_id与file_name的对应关系要对齐。我习惯转换后跑一遍校验脚本,检查每张图的标注框是否超出图像边界、是否存在空的bbox、类别id是否越界。

从VOC转YOLO txt的脚本逻辑并不复杂,核心代码如下:

import os import xml.etree.ElementTree as ET def voc_to_yolo(xml_path, out_path, classes): tree = ET.parse(xml_path) root = tree.getroot() width = float(root.find("size/width").text) height = float(root.find("size/height").text) lines = [] for obj in root.findall("object"): name = obj.find("name").text if name not in classes: continue box = obj.find("bndbox") x1 = float(box.find("xmin").text) y1 = float(box.find("ymin").text) x2 = float(box.find("xmax").text) y2 = float(box.find("ymax").text) x_center = ((x1 + x2) / 2) / width y_center = ((y1 + y2) / 2) / height box_w = (x2 - x1) / width box_h = (y2 - y1) / height lines.append(f"{classes.index(name)} {x_center:.6f} {y_center:.6f} {box_w:.6f} {box_h:.6f}") with open(out_path, "w", encoding="utf-8") as f: f.write("\n".join(lines)) classes = ["crack"] voc_to_yolo("000001.xml", "000001.txt", classes)

这类脚本运行完之后,一定要对生成的txt抽样可视化,把框画回原图看一遍。坐标计算有没有问题、归一化方向对不对,光看数字很难发现,画图一目了然。

3.4 标注质量抽检

标注完成不等于交付完成。我习惯按10%的比例抽检,抽检时把标注框画回原图,肉眼过一遍,重点关注两类问题:框的位置偏移和遗漏的裂缝。位置偏移在细长目标上太常见了,框稍微偏一点,IoU就跌得很难看,模型训练时正样本质量被整体拉低。遗漏裂缝的后果更严重,模型会把漏标的裂缝学成背景,训练出来就是漏检。

抽检不合格的批次必须退回重标,这个环节不能省。6000多张图片的标注量,人工全部复查一遍成本太高,但10%抽检加自动校验的组合已经足够拦住绝大多数低级错误。我在整理过程中发现,标注质量问题通常是系统性的:某一个时间段内标出来的数据可能存在同样的偏移规律,所以抽检资料要按标注人员和批次分组,而不是简单随机。

4. 数据划分:训练、验证、测试集怎么分才不"漏水"

4.1 随机划分的最大陷阱

数据集划分看最简单,实际最容易被忽视。最典型的错误是直接按图片随机划分,文件夹里train、val、test随机扔。外墙图片有一个特性:同一面墙连续拍摄的照片高度相似,左右相差不到几十厘米。如果随机划分,这些高度相似的图片会被拆到训练集和验证集两边,模型在验证集上表现很好,换到完全没见过的楼栋时效果立刻打折扣。这就是数据泄漏,后果是评估指标虚高,部署后模型真实能力被高估。

我在一些团队分享时见过类似的案例:验证集mAP达到0.85,信心满满去现场测试,换一栋楼直接掉到0.5。根源不在模型,在数据划分方式。

4.2 按采集批次与楼栋分组

我采用的策略是按"采集批次+楼栋"分组,分组之后再划分。也就是说,同一栋楼、同一次采集批次里的所有图片,只能进入同一个集合。整套数据按约8:1:1的比例拆分。6000多张图片最终分发为训练集约4800张,验证集约600张,测试集约600张。

这里还要考虑场景分布的均衡问题。我会专门把测试集里的楼栋类型设置成训练集少见甚至未见过的组合,比如训练集以住宅涂料墙为主,测试集里多放一些厂房水泥墙面,用来检验模型跨场景泛化能力。目标检测模型最怕的就是只在一种表面材质上表现好、换材质就崩。

4.3 划分结果的核验方法

划分完还要核验,不能只看数量。我写了一个统计脚本,分别统计三个集合里的图片数、标注框数、每张图平均框数,确认三者分布接近。如果训练集平均每张图3个框,验证集却只有1.5个框,说明分组方式有问题,需要重新调整。

另外还要检查测试集里是否出现了与训练集来自同一次连续拍摄的图片。我主要通过文件名前缀加时间戳的方式控制,分组时按前缀聚合,从源头切断泄漏。每个采集批次的图片命名前缀不同,同批次里再细分楼栋编号,这样后面的人拿到数据也能清楚知道哪些图片来自同一个场景,不会稀里糊涂做随机划分。

这样的评估结果才有参考价值。这也是我在这套数据集的说明里把"已划分"单独强调的原因:划分不是简单按数量切三份,而是有场景隔离逻辑在里面的。

5. 用YOLOv8实测:从配置文件到训练结果

5.1 目录组织与环境依赖

拿到数据之后,按目标检测训练的标准目录结构放好就行。以YOLOv8为例:

exterior_crack/ ├── images/ │ ├── train/ │ ├── val/ │ └── test/ ├── labels/ │ ├── train/ │ ├── val/ │ └── test/ └── exterior_crack.yaml

环境依赖使用Python 3.10和ultralytics包,PyTorch 2.x即可,安装命令很常规:

pip install ultralytics

CUDA版本按自己的显卡驱动选择对应的PyTorch版本,这一步卡过很多人,建议开始训练前先确认一下torch.cuda.is_available()的输出是True。

5.2 数据集配置文件的写法

YOLO的数据集配置文件是一个YAML,内容很简单:

path: /data/exterior_crack train: images/train val: images/val test: images/test nc: 1 names: 0: crack

path字段可以写绝对路径,也可以写成项目根目录的相对路径,但train、val、test字段建议都用相对路径,否则换机器训练时容易路径错乱。nc表示类别数,names里面每个索引对应labels里txt文件的第一个数字。这里最容易出的问题是类别索引没对齐,比如names里crack排在第0位,标注文件第一列写成1,模型就会去找一个不存在的第二类,直接把训练跑崩。

5.3 训练命令与参数选型

我实测下来,YOLOv8n、YOLOv8s、YOLOv8m都跑过。以n模型为例,命令如下:

yolo detect train data=exterior_crack.yaml model=yolov8n.pt imgsz=640 batch=16 epochs=200 patience=50

参数方面有几个关键点。imgsz=640是默认推荐,兼顾速度和精度;如果想提升小裂缝召回,可以试到960,但显存占用和训练时间会明显上升。batch=16在常见8G显存下刚好卡在边缘,不够就降到8。epochs=200搭配patience=50,Early Stopping生效时能提前结束,避免无效等待。预训练权重建议从前一个通用模型的权重开始,不要随机初始化,外墙裂缝的纹理特征虽然和通用数据集差异大,但底层边缘、梯度特征仍然可以迁移,这是训练收敛速度的关键。

5.4 实测指标与解读

一组代表性测试集结果如下:

模型输入尺寸mAP50mAP50-95训练耗时参考
YOLOv8n6400.620.34约2.5小时
YOLOv8s6400.670.38约4小时
YOLOv8m6400.720.42约8小时

这个数字初看不算高,但裂缝检测本身就比人、车这类紧凑目标难,mAP50达到0.7以上已经具备工程筛选价值。mAP50-95通常只有0.3到0.4,这并不代表模型失败,而是因为裂缝的标注框是长条形的,预测框和真实框在IoU阈值提高后很难完全贴合,mAP50-95天然偏低。评估时建议重点看mAP50、Recall以及小目标类别的AP,而不是死磕mAP50-95。

训练出来的权重直接推理大图时,需要配合滑窗裁图,不要直接整图缩放输入。整图缩放会把短裂缝压成几个像素的短线,模型根本识别不出来。滑窗裁剪、逐块推理、再对重叠区域做NMS合并,是这类细长目标部署时的标准操作。

6. 裂缝检测模型的难点复盘与部署建议

6.1 小裂缝目标:缩小输入尺寸是最大的陷阱

训练时如果把大图直接缩放成640x640,很多短裂缝会变成不到30像素宽的短线,模型很难学到稳定的特征。训练阶段建议保持多尺度训练,ultralytics默认带尺度扰动,让它开着就行。推理阶段也不要省这一步,用滑窗裁图加逐块推理加NMS合并结果,比直接把大图缩进去效果好得多。滑窗的步长建议设成图片尺寸的50%左右,保留足够的重叠,避免裂缝主体恰好落在两个tile的拼接位置。

6.2 误检来源分析

训练完容易出现两类误检:把涂料流坠、水渍误检成裂缝,把窗框边缘、管线阴影误检成裂缝。水渍和裂缝在外观上都是深色线性痕迹,模型如果没见过足够多的负样本,很难区分。解决办法有两个方向:一是扩充负样本,把外墙常见干扰物单独建一个背景集加进训练;二是在部署阶段增加后处理规则,比如对检测框的长宽比、面积占比设置阈值,过滤掉明显不合理的检测结果。

实际项目里,误检和漏检是一个权衡。外墙检测业务场景通常更怕漏检,因为漏掉一条真裂缝可能带来安全风险。所以部署时我会把置信度阈值适当调低,宁可多出一些候选框交给人审,也不让裂缝漏掉。

6.3 标注一致性的长期影响

我后来反复对比发现,标注一致性对模型精度的影响甚至超过模型结构选择。同一张图,如果A标注员画的长框、B标注员画得更紧凑,模型会对"框该多大"无所适从。前面提到的标注对齐测试,强烈建议在项目启动前做一次。让参与标注的人各标同一批20张图,逐框对比差异,然后全部写进标注规范,这一小时的工作比后期返工省力得多。

另外,数据集版本管理也要跟上。6000多张图,今天改几张标注,明天添一批新图片,如果没有版本管理,后面回溯训练结果时根本不知道模型是在哪一版数据上训出来的。我用的办法很简单,每轮修改后打一个版本号,训练时把数据版本号写进模型名称里,比如yolov8n_v3.pt,一目了然。

6.4 部署阶段的流程设计

检测模型跑通只是一个起点,工程上还要考虑怎么和业务结合。比较务实的流程是:无人机或定期巡检采集视频,抽帧后先按区域切块推理,检测到裂缝的帧保留,输出带坐标的截图,由人工审核确认,再安排现场测量宽度。目标检测的作用是把人工从"逐面墙找裂缝"变成"看模型筛出的候选框",效率提升明显,同时保留人工复核环节,符合工程安全需求。

最后再分享一个我在实际使用中的体会:这套数据从采集到最终训出可用的模型,中间踩过的坑比预期多不少。最大的收获是认识到数据集的质量决定模型上限,而质量的核心不在数量大小,在于每个环节是否有人较真。标注规范定得细、数据划分防泄漏、负样本比例合理,这些没有一个是能靠堆图片数量解决的。后续如果想把模型能力延伸到渗水、空鼓等新缺陷类型,也需要沿用同样的流程再补数据,而不是简单把新图片塞进旧的训练集里了事。

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询