ARTICLE DETAIL

资讯详情

深耕网站建设与运营推广的一线实战洞察。

电动车摩托车违规检测数据集:YOLO训练与标注质检实战

电动车摩托车违规检测数据集:YOLO训练与标注质检实战 简介本资源面向计算机视觉与目标检测方向的开发者、学生及算法工程师提供一套可直接用于YOLO训练的电动车、摩托车违规行为图像数据集聚焦不戴头盔、骑行中使用手机等常见违规场景适合开展交通违规检测、安全监控等实战项目。压缩包共1883个文件包含940张jpg图像、941个txt标注文件、1个可视化py脚本和1个png图片整体约56.63MB数据按YOLOv5目录结构组织划分为约700张训练集与180张验证集并附类别class文件可直接接入检测流程。可视化脚本无需修改即可随机读取图片并绘制边界框便于快速核验标注质量。目前已有531人学习下载配套YOLOv5改进实战专栏能帮助读者从数据准备到模型训练完整跑通违规目标检测任务。1. 电动车摩托车违规检测数据集从拿到压缩包到跑通第一轮训练路口监控里电动车闯红灯、摩托车逆行、骑手不戴头盔这些场景做算法落地时最头疼的往往不是模型结构而是手里没有一份标注干净、类别明确、拿来就能喂给 YOLO 的数据。这份资源就是冲着这个痛点来的它提供了一批电动车与摩托车违规目标的图像已经按训练/验证/测试划分好附带类别 class 文件和数据可视化脚本。适合正在做交通违规检测、智慧路口项目或者想拿真实场景数据练手 YOLO 训练流程的从业者。你不需要自己从视频抽帧、标注、划分解压后改几个路径就能进入训练环节。下面我按实际拆包顺序把目录结构、类别定义、可视化校验、训练配置和几个容易翻车的地方讲清楚。2. 拆开压缩包先看什么目录结构、class 文件与划分逻辑拿到一份目标检测数据集我习惯先不急着写训练脚本而是把目录结构和标注文件翻一遍。这一步花十分钟能省掉后面几小时的报错排查。这份资源的组织方式比较标准属于 YOLO 系列常见的 images/labels 平行目录结构配合 data.yaml 描述类别和路径。2.1 目录层级与文件对应关系解压后典型结构大致是这样不同版本可能略有差异以实际为准dataset/ ├── images/ │ ├── train/ │ ├── val/ │ └── test/ ├── labels/ │ ├── train/ │ ├── val/ │ └── test/ ├── classes.txt ├── data.yaml └── visualize.pyimages 下每个子目录放 jpg/png 原图labels 下同名 txt 放标注。YOLO 格式的标注是每行一个目标class_id x_center y_center width height后四个都是归一化到 0~1 的相对坐标。这里有个高频坑图片和标注必须同名只差扩展名。如果 images/train 里有001.jpglabels/train 里就必须有001.txt否则训练时这张图会被当成负样本或者直接报错跳过。classes.txt 是纯文本一行一个类别名行号即 class_id。data.yaml 则是训练入口配置通常长这样path: ./dataset train: images/train val: images/val test: images/test nc: 3 names: [electric_bike_violation, motorcycle_violation, helmet_missing]nc是类别数names顺序必须和 classes.txt 完全一致。我见过有人改了 names 顺序但没改标注里的 class_id结果模型把电动车识别成摩托车mAP 看着还行但业务全错。改类别定义时classes.txt、data.yaml 的 names、以及标注文件里的 id 三者要同步动。2.2 划分比例与类别分布检查资源已经划分好 train/val/test省去了自己 split 的步骤。但划分好不代表分布合理。常见做法是训练前统计一下每个类别的实例数看有没有严重长尾。可以用几行脚本快速过一遍import os from collections import Counter label_dir dataset/labels/train counter Counter() for f in os.listdir(label_dir): if not f.endswith(.txt): continue with open(os.path.join(label_dir, f)) as fp: for line in fp: cls_id int(line.split()[0]) counter[cls_id] 1 print(类别实例分布:, dict(sorted(counter.items())))这段逻辑很直白遍历训练集标注目录读每行第一个字段作为类别 id 计数。跑完如果发现某个类别只有几十个实例而另一个有几千个那训练时小类别大概率学不好。解决办法不是硬训而是先确认这个类别是不是真的这么少或者考虑过采样、类别权重。参数上没什么可调的重点看输出分布是否符合业务预期。提示统计时把 train/val/test 分别跑一遍如果 val 里某个类别一个实例都没有验证指标会失真这种划分需要重新调整。2.3 可视化脚本怎么用资源带的数据可视化脚本是校验标注质量最直接的工具。它一般做两件事把归一化坐标还原成像素坐标画框以及在框上标类别名。核心逻辑大概是这样import cv2 import os def draw_boxes(img_path, label_path, classes, save_path): img cv2.imread(img_path) h, w img.shape[:2] with open(label_path) as f: for line in f: cid, xc, yc, bw, bh map(float, line.split()) x1 int((xc - bw / 2) * w) y1 int((yc - bh / 2) * h) x2 int((xc bw / 2) * w) y2 int((yc bh / 2) * h) cv2.rectangle(img, (x1, y1), (x2, y2), (0, 255, 0), 2) cv2.putText(img, classes[int(cid)], (x1, y1 - 5), cv2.FONT_HERSHEY_SIMPLEX, 0.6, (0, 255, 0), 2) cv2.imwrite(save_path, img)关键点在坐标还原YOLO 存的是中心点加宽高画框要先算左上角和右下角。xc*w是中心 x 像素减去bw*w/2才是左边界。如果画出来的框整体偏移或者大小不对八成是这里算错了或者图片在标注后被缩放裁剪过。跑几十张图肉眼扫一遍重点看有没有框错位、漏标、类别标反的情况。这一步别省标注脏数据是后面 mAP 上不去的头号元凶。3. 把数据喂给 YOLO环境、配置与训练命令数据检查完接下来是让它真正跑起来。这一章按环境准备、配置修改、启动训练、看结果四步走每步都给可抄的命令和参数说明。不管你用的是 YOLOv5、v8 还是更新的版本数据组织逻辑是通的差异主要在训练命令和配置文件字段名上。3.1 环境与依赖准备先确认 Python 和 PyTorch 版本匹配。GPU 训练的话CUDA 版本要和 PyTorch 对应这个不匹配是最常见的「装完跑不起来」。常见做法是用 conda 建独立环境conda create -n yolo_ev python3.10 -y conda activate yolo_ev pip install torch torchvision --index-url https://download.pytorch.org/whl/cu118 pip install ultralytics opencv-python pyyamlcu118对应 CUDA 11.8如果你机器是别的版本去 PyTorch 官网查对应命令。ultralytics 这个包覆盖了 YOLOv8 及之后的训练推理接口装完yolo命令就能直接用。装完跑一句yolo checks看环境自检它会告诉你 GPU 有没有被识别、版本对不对。如果显示 CPU only 而你有显卡先查驱动和 CUDA别急着改代码。3.2 data.yaml 与训练参数配置data.yaml 前面看过结构这里补几个训练时真正影响结果的字段。以 YOLOv8 风格为例path: /abs/path/to/dataset train: images/train val: images/val test: images/test nc: 3 names: [electric_bike_violation, motorcycle_violation, helmet_missing]path建议写绝对路径相对路径在不同工作目录下启动训练时容易找不到文件。nc和names长度必须一致不一致直接报错。改完 yaml启动训练yolo detect train \ datadataset/data.yaml \ modelyolov8n.pt \ epochs100 \ imgsz640 \ batch16 \ device0 \ projectruns/ev_violation \ nameexp1逐个说参数modelyolov8n.pt是预训练权重n 是最小号显存紧张先用它epochs100是训练轮数小数据集容易过拟合可以配合早停imgsz640是输入尺寸违规检测里小目标多的话可以提到 960但显存和速度要权衡batch16按显存调OOM 就减半device0指定第一块 GPUCPU 训练写cpu。project和name决定结果保存路径方便多次实验对比。3.3 训练过程看什么指标训练启动后终端会刷每个 epoch 的损失和指标。重点盯三个box_loss定位损失、cls_loss分类损失、以及验证集上的mAP50和mAP50-95。前几十个 epoch 损失下降快是正常的后面趋于平缓。如果cls_loss一直不降多半是类别定义或标注有问题回去查 class_id 有没有越界。如果训练集 mAP 很高但验证集很低那是过拟合加数据增强或者减模型容量。训练完在runs/ev_violation/exp1/下会有weights/best.pt和last.pt还有混淆矩阵、PR 曲线等图。混淆矩阵能直接看出哪个类别容易被混比如电动车违规和摩托车违规如果互相混得多说明这两类视觉特征太接近要么合并类别要么补充区分度高的样本。3.4 推理验证与结果导出拿 best.pt 跑几张测试图确认模型真的能用yolo detect predict \ modelruns/ev_violation/exp1/weights/best.pt \ sourcedataset/images/test \ conf0.25 \ saveTrueconf0.25是置信度阈值低于它的框不输出。违规检测场景里漏检和误检的代价不同如果业务更怕漏检就把阈值调低到 0.15 左右宁可多报也别放过如果误报会触发大量人工复核就提到 0.4 以上。这个阈值没有标准答案要拿一批真实场景图跑一遍看误报漏报的平衡点在哪。结果默认存到runs/detect/predict可以直接翻图核对。4. 避坑与排查标注、路径、显存、指标四类高频问题这一章是我自己踩过和帮别人排查过的真实问题按「现象 → 原因 → 解决」写。数据集类项目翻车大多不在模型而在数据和环境这些看起来不起眼的地方。4.1 训练报「No labels found」或大量图片被跳过现象启动训练后提示找不到标注或者日志里 warning 说某些图片没有对应 label 被忽略。原因images 和 labels 目录层级不对应或者图片和标注文件名不一致。YOLO 找标注是按路径替换images为labels再换扩展名任何一环对不上就找不到。解决写个脚本核对两边文件名集合是否一致把差集打出来。常见的是图片是.jpeg而标注按.jpg命名或者有的图根本没标。差集里的图要么补标要么从训练集移除。4.2 画出来的框整体偏移或大小不对现象可视化脚本跑出来框的位置和实际目标对不上整体偏一个方向或者框明显偏大偏小。原因坐标还原公式用错或者图片在标注后被 resize 过但标注没同步更新。YOLO 归一化坐标是相对原图的如果原图被裁过坐标就失效了。解决先拿一张图手动算一遍中心点和宽高和标注文件对比。确认公式是x1(xc-bw/2)*w。如果公式没错检查图片尺寸是否和标注时一致不一致的图要重新标注或从数据集剔除。4.3 训练中途 CUDA out of memory现象训练跑着跑着报显存不足进程被杀。原因batch 太大、imgsz 太高或者验证阶段同时占显存。小显存卡跑 640 加 batch16 很容易爆。解决先把 batch 减到 8 或 4再把 imgsz 降到 512 试。还可以开混合精度ampTrue多数版本默认开能省不少显存。如果还不行换更小的模型比如从 s 换到 n。别硬扛大 batch训练稳定性比吞吐重要。4.4 mAP 虚高但实际检测一塌糊涂现象验证集 mAP 看着不错但拿真实场景图一跑漏检误检严重。原因验证集和训练集分布太接近甚至来自同一段视频的相邻帧模型记住了背景而不是目标。或者类别定义太粗把不同违规行为混成一类。解决验证集要尽量独立最好来自不同路段、不同时段。类别定义按业务需求拆细比如「不戴头盔」和「闯红灯」分开别都塞进「违规」一类。另外看看混淆矩阵如果某类 recall 很低针对性补样本。5. 进阶技巧用可视化脚本反查标注质量与类别平衡数据可视化脚本很多人只拿来画几张图看看其实它能当标注质检工具用而且比肉眼翻图高效得多。我的习惯是把它改造成批量统计加异常检测一次跑完整个数据集把可疑样本挑出来。具体做法是在画框逻辑外面套一层统计记录每张图的框数量、每个类别的实例数、框的宽高分布。框数量异常多比如一张图几十个框或者异常少零框的图单独列出来。宽高比特别极端的框也值得怀疑比如宽高比超过 10:1 的很可能是标注时拉歪了。下面这段在原来画框基础上加了统计和异常标记import os import cv2 import numpy as np def audit_dataset(img_dir, label_dir, classes, area_thresh0.001): stats {total_imgs: 0, empty_labels: [], tiny_boxes: [], cls_count: {}} for f in os.listdir(label_dir): if not f.endswith(.txt): continue stats[total_imgs] 1 label_path os.path.join(label_dir, f) img_path os.path.join(img_dir, f.replace(.txt, .jpg)) with open(label_path) as fp: lines [l for l in fp if l.strip()] if not lines: stats[empty_labels].append(f) continue for line in lines: cid, xc, yc, bw, bh map(float, line.split()) stats[cls_count][int(cid)] stats[cls_count].get(int(cid), 0) 1 if bw * bh area_thresh: stats[tiny_boxes].append((f, bw * bh)) return stats result audit_dataset(dataset/images/train, dataset/labels/train, [electric_bike_violation, motorcycle_violation, helmet_missing]) print(空标注文件:, result[empty_labels][:10]) print(过小框数量:, len(result[tiny_boxes])) print(类别分布:, result[cls_count])area_thresh0.001是相对面积阈值小于千分之一的框基本是误标或者目标太小不值得学。跑完看三个输出空标注文件列表、过小框数量、类别分布。空标注要么补标要么删图过小框考虑过滤类别分布如果某类占比低于 5%训练时要么过采样要么调类别权重。这套质检流程我一般放在训练之前强制走一遍。有次偷懒没跑训完发现验证集里混进了一批标注错位的图mAP 卡在 0.4 上不去回头查标注又花了大半天。从那以后我每次拿到新数据集都先跑一遍统计加可视化确认干净了再进训练。数据这关过了模型调参才有意义。希望这份资源和这套流程能帮你少走点弯路。本文还有配套的精品资源点击获取
返回列表