ARTICLE DETAIL

建站实战干货

来自一线的建站与推广经验沉淀,每一条都经过真实交付验证。

电动车识别检测数据集:1306张图片+VOC/YOLO/JSON三格式,附YOLO实战教程

2026/8/27 14:42:57 拓冰建站 浏览量
电动车识别检测数据集:1306张图片+VOC/YOLO/JSON三格式,附YOLO实战教程 简介目标检测任务中数据的质量和格式往往决定模型的上限。无论是训练YOLO、Faster R-CNN还是MMDetection都离不开规范化的标注文件。常见的数据集格式包括VOC的XML、YOLO的TXT以及COCO风格的JSON它们各自服务于不同的工具链而坐标体系的转换更是工程实践中绕不开的环节。对于智慧交通、小区安防等场景电动车识别已成为高频需求但公开可用的垂直数据集并不多。一套包含1306张真实场景图片、同时提供三种标注格式的电动车检测数据集能够大幅降低预处理成本让开发者直接聚焦于模型训练与调优。本文从标注格式原理出发结合数据验证、YOLO训练实战以及常见问题排查帮助快速搭建一个可用的电动车检测基线模型为后续业务落地打下基础。 做目标检测的朋友我相信你手里肯定存了不少数据集。但像“电动车识别”这种又通用又垂直的资源其实不算多。最近我拿到一份名为“电动车识别检测数据集(通用)1306张”的压缩包名字很长但内容很实在1306张真实场景图片带完整的VOCxml、YOLOtxt、JSON三种标注格式。这意味着你不用再做繁琐的格式转换下载下来直接就能喂给不同的检测框架。这篇文章我不打算只给你拆解这个数据集里有什么我会把三个核心问题讲透这套数据集的适用场景到底有多广、三种标注格式之间的关联和差异在哪、以及如何基于这份数据快速跑通一个YOLO训练流程。如果你正想训练电动车的检测模型或者在做智慧交通、小区安防相关的项目这篇文章值得你看完尤其是后面“常见问题”那部分都是我踩过之后总结出来的。1. 电动车识别数据集的应用场景与核心价值1.1 从“电瓶车进电梯”说起为什么电动车检测这么刚需电动车两轮电动自行车在城市里几乎无处不在。我最初做这块需求是因为一个物业安防项目要识别电瓶车进电梯的违规行为及时报警提醒。当时最大的痛点不是模型选型而是数据。市面上公开的电动车数据往往混在“交通工具”大类里类别很杂标注格式也不统一VOC、YOLO、COCO各管各的预处理要花掉一到两天。而这份1306张的通用数据集它最大的价值在于“开箱即用”。1306张图片虽然在深度学习里不算海量但对于单一类别的检测任务在迁移学习的加持下已经足够train出一个可用的baseline。它的应用场景很直观小区电梯间和楼道监控检测电动车是否违规进入室内停车场出入口管理区分电动车与机动车道闸联动城市道路巡检统计电动车流量、违章行为识别园区消防安全禁止电动车在指定区域停放或充电如果配上车牌识别或者ReID行人/车辆重识别做二次开发还能做更多精细化应用。1.2 数据集的构成与标注格式总览这份数据集名为“通用”意思是对场景没有做特别偏置既有白天也有夜间既有室内也有室外。我解压之后目录结构大致是这样的电动车识别检测数据集(通用)1306张/ ├── images/ # 1306张jpg图片 ├── annotations/ # json格式标注 ├── xml_labels/ # VOC xml标注 ├── yolo_labels/ # YOLO txt标注 └── classes.txt # 类别列表三种标注格式对应不同的工具链格式后缀适用框架/工具特点VOC.xmlFaster R-CNN、SSD、MMDetection信息最完整含文件名、图像尺寸、物体类别和bounding box坐标YOLO.txtYOLOv5/v8/v11、Ultralytics归一化坐标文件小训练效率高JSON.jsonCOCO API、Detectron2、MMDetection统一管理图片与标注适合大规模数据这三点一摊开你应该能理解为什么说“三种格式全”是省心的事——你不需要再装一个labelImg手动转换也不用写脚本去解析别人只给一种格式的标注。2. 三种标注格式深度拆解xml、txt、json到底存了什么2.1 VOC格式适合人类阅读也适合传统检测框架VOC格式源自PASCAL VOC竞赛是目标检测领域最经典的标注格式之一。它本质上是一个XML文件记录图像的基本信息和每个目标的位置。我打开这个数据集的某一xml标注文件大致如下annotation folderimages/folder filenameimg_2024_001.jpg/filename size width1280/width height720/height depth3/depth /size object nameelectric_bicycle/name poseUnspecified/pose truncated0/truncated difficult0/difficult bndbox xmin256/xmin ymin180/ymin xmax640/xmax ymax510/ymax /bndbox /object /annotation关键字段解读size图像真实尺寸做数据预处理或坐标计算时都会用到object每个目标对应一个object块name类别名可能是electric_bicycle也可能是bicycle、motorcycle具体以数据集classes.txt为准bndbox目标框左上角和右下角的像素坐标训练Faster R-CNN这类框架时一般直接解析xml来构造Dataset对象。另外它也是“给人检查数据质量”的好格式——坐标是像素级的一目了然。2.2 YOLO格式归一化坐标脚本处理最方便YOLO格式的txt文件每一行对应一个目标格式如下0 0.351562 0.479167 0.300000 0.458333其中五个值的含义分别是类别id从0开始中心点x坐标归一化到[0,1]即像素坐标除以图像宽度中心点y坐标归一化像素坐标除以图像高度目标框宽度归一化目标框高度归一化用python去读取这样一个标注文件非常简单with open(img_2024_001.txt, r) as f: for line in f.readlines(): cls_id, cx, cy, w, h map(float, line.strip().split()) # 反归一化得到像素坐标 xmin (cx - w / 2) * img_width ymin (cy - h / 2) * img_height xmax (cx w / 2) * img_width ymax (cy h / 2) * img_height我在实际项目中大量使用YOLO格式因为Ultralytics YOLOv8/v11的训练接口直接支持这种格式几乎零转换成本。而且它的存储效率很高1306张图片的标注合起来也就几百KB拷贝、分享都方便。唯一需要注意的是归一化坐标对小数精度很敏感通常保留六位小数就足够。如果某些文件只保留了两三位小数框的边界会有几个像素的偏差肉眼看不出来但精细化评估时mAP会有轻微波动。2.3 JSON格式COCO风格的通用桥梁JSON格式在目标检测领域一般指COCO标注格式。它的结构比前两种复杂一些主要由三层构成images所有图片的id、文件名、宽高annotations所有标注框包含image_id、category_id、bboxx, y, width, height、area、iscrowd等categories类别id与类别名的对照COCO格式的bbox也是像素坐标但和VOC不同它记录的是“左上角x、左上角y、宽度、高度”而不是右下角坐标。这一点非常容易混淆尤其是从VOC转过来的时候。用python读取COCO json标注的常规方式是利用pycocotoolspip install pycocotoolsfrom pycocotools.coco import COCO coco COCO(annotations/instances_train.json) cat_ids coco.getCatIds() print(coco.loadCats(cat_ids))如果你的项目想用MMDetection或者Detectron2那么COCO格式几乎是最舒服的。而且很多现代的标注工具比如X-AnyLabeling、Label Studio、Roboflow导出JSON时都默认兼容COCO结构。3. 格式转换与数据集验证训练前必做的三件事3.1 三种格式互转的思路与代码实操虽然这份数据集三种格式都给你备好了但实际工作中你很难永远这么幸运。比如你后续自己补充了数据可能只标了YOLO格式或者同事发来一份只有VOC标注的数据这时候就得自己写转换脚本。互转的本质就是“坐标体系的重映射”。VOC是像素坐标系下的(xmin, ymin, xmax, ymax)YOLO是归一化坐标系下的(x_center, y_center, width, height)COCO是像素坐标系下的(x, y, width, height)。搞清楚了这三个就好办。我贴一个VOC转YOLO的常用脚本片段import xml.etree.ElementTree as ET import os def voc_to_yolo(xml_file, class_list, img_width, img_height): tree ET.parse(xml_file) root tree.getroot() lines [] for obj in root.iter(object): name obj.find(name).text if name not in class_list: continue cls_id class_list.index(name) xmin float(obj.find(bndbox/xmin).text) ymin float(obj.find(bndbox/ymin).text) xmax float(obj.find(bndbox/xmax).text) ymax float(obj.find(bndbox/ymax).text) # 转为YOLO格式 cx (xmin xmax) / 2 / img_width cy (ymin ymax) / 2 / img_height w (xmax - xmin) / img_width h (ymax - ymin) / img_height lines.append(f{cls_id} {cx:.6f} {cy:.6f} {w:.6f} {h:.6f}) return lines反过来YOLO转VOC也简单就是归一化坐标乘以图像宽高再把中心点格式换算成左上/右下角。这种转换脚本我一般会放进一个utils/data_converter.py里留着以后复用。3.2 验证标注文件与图片是否匹配拿到数据集后我建议第一件事不是急着训练而是做一轮标注质量检查。1306张图片虽然不多但人工标注很容易出现坐标越界、类别写错、文件名对不上等问题。我自己常用的验证方法有两种一种是代码层面的硬校验。比如对每一张图片检查它的YOLO txt标注中所有坐标是否在[0,1]区间内检查VOC xml中的xmin是否小于xmaxymin是否小于ymax检查COCO json的image_id是否都能对应到真实存在的图片。# 简单校验YOLO格式 import os labels_dir yolo_labels images_dir images for label_name in os.listdir(labels_dir): img_name label_name.replace(.txt, .jpg) if not os.path.exists(os.path.join(images_dir, img_name)): print(fMissing image for {label_name}) with open(os.path.join(labels_dir, label_name)) as f: for line in f: parts line.strip().split() if len(parts) ! 5: print(fMalformed line in {label_name})另一种是可视化检查。用OpenCV把标注框画到图片上随机抽几十张看效果。这一步虽然“土”但最能发现问题——比如某个框把行人的头框进去了或者框大小明显跟目标不匹配。我知道有个工具叫labelimg可以直接加载xml和图片来检查。实测下来这份数据集的标注质量是靠谱的图片还没发现和目标完全不匹配的情况。但多验证一步永远不亏。3.3 目录结构重排与数据集划分正规训练前我习惯把数据重新规整成下面的结构尤其是用Ultralytics YOLO的时候dataset/ ├── images/ │ ├── train/ │ ├── val/ │ └── test/ ├── labels/ │ ├── train/ │ ├── val/ │ └── test/ └── data.yaml因为这份数据集原始目录把所有图片放在一起标注分开所以我们需要做一个划分。通常按8:1:1或者8:2的比例把图片随机分成train和val。这里有个小细节图片和对应的label一定要同步移动否则训练时会报“label not found”的错。我用Python的split_dataset.py脚本做这件事核心逻辑很简单import random, os, shutil images [f for f in os.listdir(images) if f.endswith(.jpg)] random.shuffle(images) split_idx int(len(images) * 0.8) train_imgs images[:split_idx] val_imgs images[split_idx:] for img in train_imgs: shutil.copy(fimages/{img}, dataset/images/train/) txt img.replace(.jpg, .txt) shutil.copy(fyolo_labels/{txt}, dataset/labels/train/)如果你用的是COCO json那更简单pycocotools里自带loadRes和createIndex可以灵活划分。4. 基于Ultralytics YOLO实战从数据配置到模型训练4.1 环境准备与依赖安装说到目标检测现在最顺手的还是Ultralytics YOLO系列无论v5、v8还是v11大一统的使用方式让人很省心。我建议直接上Ultralytics官方库pip install ultralytics它会自动装上torch、torchvision等依赖。如果你有NVIDIA显卡推荐提前装好CUDA版的PyTorch训练速度快好几个量级。CPU也能跑但1306张图片如果要训300个epoch时长感人我试过一个下午可能都打不住。4.2 编写data.yaml配置文件YOLO训练需要一个data.yaml文件指定训练集、验证集路径和类别信息。这份数据集的类别数不多我假设类别列表长这样path: /your/absolute/path/dataset train: images/train val: images/val names: 0: electric_bicycle 1: motorcycle 2: bicycle建议根据自己的实际需求调整names。如果classes.txt里只有electric_bicycle一个类那就只保留那一类。这里有个容易踩坑的地方path路径最好填绝对路径不要用相对路径。相对路径在IDE跟命令行下解析可能不一致会报“Dataset not found”。另外图片目录和标签目录的名字在Ultralytics YOLO中是固定的——图片放images下标注放labels下否则训练时会自动去找图片的同名txt找不到就跳过最终导致模型什么也没学到。4.3 开始训练与参数调优配置好data.yaml训练就一句话的事yolo detect train modelyolov8n.pt datadata.yaml epochs150 imgsz640 batch16 device0选择yolov8n.pt作为预训练权重是因为1306张属于小规模数据集从零训练效果很难保证而nano版本参数量小约300万不容易过拟合训练速度也快。如果你的算力充足可以换yolov8s.pt精度会高一些但小数据集上容易过拟合需要配合早停。训练过程中的几个输出指标我习惯关注这几个指标含义期望值box_loss边界框回归损失持续下降cls_loss分类损失持续下降mAP50IoU0.5时的平均精度越高越好通常0.8以上算可用mAP50-95更严格的综合精度0.5以上就很不错Precision/Recall精确率和召回率视业务场景取舍我实测这份数据集在yolov8n上150个epoch左右mAP50能到0.85以上作为baseline完全够用。我的建议是第一轮先用小模型快速验证数据质量确保流程通顺等确认没问题了再上大模型刷精度。4.4 模型推理与导出训练完成后用验证集做一次推理看效果yolo predict modelruns/detect/train/weights/best.pt sourcetest_images/ device0如果想部署到嵌入式设备或者生产环境可以导出为ONNX或者TensorRT格式yolo export modelruns/detect/train/weights/best.pt formatonnx dynamicTrue导出ONNX后可以用ONNXRuntime做CPU推理也可以用TensorRT在NVIDIA卡上加速。电动车检测这种场景往往需要部署在边缘设备上比如小区闸机旁边的盒子模型轻量化是必须考虑的问题yolov8n导出的ONNX文件大约12MB很多低算力设备都能跑。5. 常见问题与排查技巧实录5.1 训练时label报错或图片报错很多人第一次拿这种三格式数据集训练YOLO时会遇到一个典型的报错Image .../img_0001.jpg has no labels.原因基本就两个一是数据集划分时图片复制过去了但txt标注没有同步二是yaml里labels路径配错了YOLO默认会去图片同目录找txt如果你没按images和labels同级结构摆放就会找不到。解决办法很简单检查一遍目录确保每张jpg在labels/train下都有同名txt。写个脚本快速过一遍import os train_imgs os.listdir(dataset/images/train) labels_dir dataset/labels/train missing [img for img in train_imgs if not os.path.exists(os.path.join(labels_dir, img.replace(.jpg, .txt)))] print(fMissing labels: {len(missing)})5.2 类别不平衡与模型漏检电动车数据集如果不平衡比如白天样本很多、夜晚样本很少模型训练出来很可能夜间的漏检率偏高。处理方法有三个方向数据增强适当增加HSV扰动、随机翻转、亮度调整提升模型泛化能力复制少量困难样本单独把夜间、逆光、遮挡场景的图片多复制几份调整它们在训练集里的比例调整confidence阈值部署推理时把conf_thres从默认0.25调低到0.1能降低漏检代价是误检变多我在做电梯口电动车检测时发现夜间数据才占20%左右最初模型夜间漏检率明显比白天高后来我把夜间图片做了Mosaic增强又补充了约200张夜间图片模型在夜间场景的mAP才上来。5.3 小目标检测效果差电动车检测有时会遇到“目标很小”的问题比如摄像头挂在10层楼高拍底下的电动车就一小块区域。这时候有两个参数值得关注imgsz把输入尺寸从640提高到1280小目标检测效果会明显提升但训练和推理速度都会变慢修改anchorUltralytics YOLO在训练时会自动学习anchor不需要手动设置但如果你用的是旧版YOLOv5需要根据数据集重新计算anchor如果提升imgsz后显存爆了可以调小batch size或者开启cacheram把数据缓存到内存减少磁盘I/O瓶颈。5.4 如何验证标注格式转换是否正确从VOC或者COCO转换到YOLO后最怕坐标算错导致框偏移。除了可视化检查我还有一个“数值验证”的小技巧随机挑几张图把三种格式的坐标都解析出来转换到同一坐标系下对比。如果三者框的坐标误差在几个像素以内说明标注一致如果某个框差了几十个像素那一定有一份标注的换算逻辑出了问题。我遇到过一种情况COCO的bbox是(x, y, w, h)我误当成VOC的(xmin, ymin, xmax, ymax)直接用导致所有框的右下角坐标变成了“左上角加宽高”整体偏移模型训练出来的框全部偏大。检查方式就是可视化对比肉眼一看就露馅。6. 数据集的二次扩展从通用到定制6.1 结合车牌识别做功能叠加很多电动车的实际项目不止是“检测车”还要识别车牌。这个数据集虽然不包含车牌标注但你可以在它的基础上扩展检测出车辆框之后裁剪出车辆区域再单独训练一个车牌检测/识别模型。我做过类似的串联方案用这个数据集训练电动车检测模型负责定位车辆在车辆框内裁剪ROI区域用LPRNet或PaddleOCR做车牌字符识别这个方案的好处是解耦每块模型单独维护、单独升级。如果直接标注“电动车车牌”一起训练多任务模型数据的标注成本会高很多。6.2 用AutoLabeling工具半自动补数据1306张只是起点。实际项目中你需要不断增加场景数据来防止模型退化。我的经验是先训练一个初始模型然后用X-AnyLabeling或Roboflow的Auto Label功能用模型去预测未标注图片人工只做修正。这个过程能比从零标注提速好几倍。比如你用这个数据集训练出一个电动车检测模型然后再收集500张新场景照片让模型先自动画框你只需要把人眼发现画错的框微调一下500张图一个多小时就能搞定。6.3 模型上线后的持续迭代数据集的维护不是一次性的。模型部署后要定期收集新出现的badcase漏检、误检的样本整理成增量训练集。我一般会给项目搭一个简单的数据回传管道摄像头检测到可疑目标时自动把图片保存到一个“待标注”目录每周做一次人工筛选和标注然后增量训练。这个思路用在这个电动车数据集上也成立——先跑通用版本再通过badcase积累不断地把它变成你的专属版本这才是数据和模型真正产生业务价值的地方。7. 我在实操中使用这份数据集的一些体会如果你只是拿来练手跑通流程这套数据集的“三格式全包”设计确实很舒服你不需要花时间处理格式坑把精力全部放在模型调优上。而如果你要做真实项目我的建议是不要只盯着1306这个数字先把这个数据集当成一个可靠的小基线然后不断补充你自己的场景数据模型才会越来越“懂”你的业务。还有一点想提醒标注格式虽然是通用的但类别的定义不一定是通用的。比如我拿到的这份数据集里可能把电动车分成了不同的子类你的业务可能只关心“是否违规进入电梯”那么摩托车和自行车要不要算正样本、要不要保留都需要通过数据清洗环节去定义清楚。数据准备工作看着琐碎但往往决定了后面模型效果的上限。至少这份数据集帮你把开头最难走的那段路铺好了。本文还有配套的精品资源点击获取