资讯详情

资讯详情

导盲犬拐杖检测数据集VOC+YOLO双格式4635张训练指南

简介本数据集面向计算机视觉开发者与辅助出行算法研究者提供导盲犬与盲杖两类目标的检测训练素材可用于行人辅助、智能拐杖或无障碍场景下的目标识别模型开发。包内共2000个文件以1999个Pascal VOC格式xml标注文件和1个说明txt为主另含对应的YOLO格式txt与jpg图片压缩包约286.53MB标注工具为labelImg采用矩形框标注。数据集共4635张图片标注类别为guide dog与whiteCane其中导盲犬框数1620、盲杖框数4430总框数6050。需注意部分图片经过增强处理且若干场景由视频截取、画面连续使用前建议仔细甄别。目前已有90人学习下载适合需要快速获取双类别检测数据、验证模型效果或进行迁移学习的读者参考使用。1. 导盲犬拐杖检测数据集4635 张 VOCYOLO 双格式到底能训出什么导盲犬拐杖检测数据集 VOCYOLO 格式 4635 张 2 类别这个标题里其实藏了三件事一个特定场景视障出行辅助器具识别、一套双格式标注Pascal VOC 的 XML 与 YOLO 的 TXT、一个中等规模样本量4635 张、2 类。它解决的不是通用目标检测问题而是让模型在街道、室内、地铁站这些复杂背景里把「导盲犬」和「盲杖/拐杖」从行人、栏杆、背包、雨伞这些高度相似的干扰物里分出来。适合谁做辅助器具识别、无障碍出行产品、边缘端视觉方案的人以及手里有 YOLO 训练流程、想找一个二类小数据集快速验证 pipeline 的工程师。4635 张不算大但二类任务下足够跑出一个能用的基线前提是你得先把 VOC 和 YOLO 两套标注对齐别一上来就train.py一把梭。2. 先搞懂 VOC 与 YOLO 双格式为什么同一个数据集要存两份标注2.1 VOC XML 和 YOLO TXT 的坐标体系差异Pascal VOC 格式每张图对应一个 XML 文件里面用bndbox记录xmin/ymin/xmax/ymax这是绝对像素坐标原点在左上角。YOLO 格式每张图对应一个 TXT每行是class_id x_center y_center width height全部是归一化到 0~1 的相对值且中心点坐标而不是角点。这两个体系不转换直接混用模型会学到完全错误的框。我一般会先确认数据集里Annotations/和labels/是否已经一一对应。常见做法是VOC 那份用来做可视化检查和标注质量审计YOLO 那份直接喂给训练脚本。因为 YOLO 训练时读的是 TXTXML 只是给你留一条「后悔药」——当发现某类漏标严重时可以回到 XML 里核对原始框。转换公式必须记牢后面写脚本要用x_center (xmin xmax) / 2 / img_w y_center (ymin ymax) / 2 / img_h width (xmax - xmin) / img_w height (ymax - ymin) / img_h提示归一化用的img_w/img_h必须来自图片真实尺寸不能想当然用 640×640。数据集里如果混了不同分辨率写死尺寸会让框整体偏移。2.2 二类别标签映射与类别不平衡的初步判断2 类别通常是guide_dog导盲犬和cane盲杖/拐杖但不同来源命名可能不一样比如dog、stick、white_cane。第一步是打开classes.txt或data.yaml确认顺序因为 YOLO 的class_id是按索引来的顺序错了模型会把狗认成拐杖。判断类别不平衡不用跑训练直接统计两个 TXT 里的行数分布# 统计每个类别的标注框数量 awk {print $1} labels/*.txt | sort | uniq -c如果输出是3200 0和1800 1说明导盲犬样本远多于拐杖训练时cls损失会被多数类主导。常见做法是在data.yaml里不手动加权而是靠数据增强里对少数类做 mosaic 和 copy-paste如果差距超过 3:1我会在损失里给少数类加cls_pw权重或者直接过采样含拐杖的图。2.3 用脚本把 VOC 转成 YOLO 并做一致性校验下面这段是我常用的转换脚本输入Annotations/和JPEGImages/输出labels/同时打印异常框import os import xml.etree.ElementTree as ET from PIL import Image VOC_DIR Annotations IMG_DIR JPEGImages OUT_DIR labels CLASSES [guide_dog, cane] # 必须和 data.yaml 顺序一致 os.makedirs(OUT_DIR, exist_okTrue) for xml_file in os.listdir(VOC_DIR): if not xml_file.endswith(.xml): continue tree ET.parse(os.path.join(VOC_DIR, xml_file)) root tree.getroot() img_name root.find(filename).text img_path os.path.join(IMG_DIR, img_name) if not os.path.exists(img_path): print(f[缺失图片] {img_name}) continue w, h Image.open(img_path).size lines [] for obj in root.findall(object): cls_name obj.find(name).text.strip() if cls_name not in CLASSES: print(f[未知类别] {xml_file} - {cls_name}) continue cls_id CLASSES.index(cls_name) bbox obj.find(bndbox) xmin float(bbox.find(xmin).text) ymin float(bbox.find(ymin).text) xmax float(bbox.find(xmax).text) ymax float(bbox.find(ymax).text) # 越界裁剪防止归一化后超出 0~1 xmin, xmax max(0, xmin), min(w, xmax) ymin, ymax max(0, ymin), min(h, ymax) if xmax xmin or ymax ymin: print(f[无效框] {xml_file}) continue xc (xmin xmax) / 2 / w yc (ymin ymax) / 2 / h bw (xmax - xmin) / w bh (ymax - ymin) / h lines.append(f{cls_id} {xc:.6f} {yc:.6f} {bw:.6f} {bh:.6f}) out_path os.path.join(OUT_DIR, os.path.splitext(xml_file)[0] .txt) with open(out_path, w) as f: f.write(\n.join(lines))逻辑说明先按filename找图拿真实尺寸再逐 object 做类别映射和越界裁剪。参数上CLASSES顺序必须和data.yaml的names完全一致否则类别索引错位。:.6f保留六位是 YOLO 官方推荐精度太少会在小目标上丢框。跑完后再用wc -l labels/*.txt对比 XML 里的 object 总数数量对不上就说明有解析遗漏。3. 用 YOLOv8 在 4635 张上跑通训练目录、配置与关键参数3.1 数据集目录结构与 data.yaml 写法YOLO 训练对目录结构有硬性要求我一般整理成下面这样避免路径玄学dataset/ ├── images/ │ ├── train/ │ └── val/ ├── labels/ │ ├── train/ │ └── val/ └── data.yamldata.yaml内容path: /home/user/dataset train: images/train val: images/val nc: 2 names: 0: guide_dog 1: canepath用绝对路径最稳相对路径在不同工作目录下容易翻车。nc必须等于类别数names的键值对顺序就是class_id。4635 张按 8:2 切训练集约 3700 张验证集约 930 张二类任务这个验证量足够看趋势。3.2 训练命令与 batch、imgsz、epochs 的取值理由yolo detect train \ datadataset/data.yaml \ modelyolov8n.pt \ epochs100 \ imgsz640 \ batch16 \ lr00.01 \ patience20 \ projectruns/guide_cane \ nameexp1参数说明modelyolov8n.pt是 nano 版4635 张二类任务用 n 或 s 就够上 l/x 容易过拟合。imgsz640是默认值如果拐杖在图中占比很小比如远景可以提到 960但显存要够。batch16在 8G 显存上比较稳爆显存就降到 8。patience20表示 20 轮验证指标不升就早停避免无效训练。lr00.01是 SGD 的初始学习率如果换成optimizerAdamW建议降到 0.001。训练时重点看box_loss、cls_loss和mAP50。二类任务里cls_loss通常降得很快如果它一直震荡多半是标注里有错类或漏标。3.3 训练中必须盯的三个指标与早停判断第一个是metrics/mAP50(B)二类任务正常能到 0.85 以上低于 0.7 说明标注或类别映射有问题。第二个是train/box_loss和val/box_loss的差距如果训练损失持续降、验证损失反弹就是过拟合加dropout或减 epoch。第三个是混淆矩阵在runs/guide_cane/exp1/下的confusion_matrix.png重点看导盲犬和拐杖有没有互相误判——如果拐杖被大量判成导盲犬通常是拐杖样本里混入了牵引绳或狗腿。注意验证集里如果某一类样本少于 50 个mAP 波动会很大别因为一轮掉点就改参数至少看 10 轮趋势。4. 避坑与排查4635 张二类数据集最容易翻车的 5 个地方4.1 现象训练 loss 正常但 mAP 始终为 0原因data.yaml里names顺序和 TXT 里的class_id对不上或者nc写成了 1。模型学到的类别索引和验证时对不上所有预测都算错类。解决打开一个 TXT 看第一列数字确认最大值是nc-1再核对names的键。改完重新训练不要接着旧权重继续。4.2 现象拐杖检测框大量偏移到图片边缘原因VOC 转 YOLO 时用了错误的图片尺寸比如 XML 里size写的是 1920×1080但实际图片被压缩成 640×640归一化分母用错。解决转换脚本里必须用PIL.Image.open(img_path).size读真实尺寸不要信 XML 里的size字段。转完随机抽 20 张用labelImg或cv2画框回看。4.3 现象导盲犬和拐杖互相误检严重原因两个类别在空间上高度共现——导盲犬通常牵着拐杖或牵引绳标注时把绳子和拐杖混为一类或者狗身上有拐杖框。解决回到 XML 里检查共现图的框归属明确「拐杖」只标白色手杖本体不标牵引绳。如果数据里确实难分考虑加一个leash类或直接合并两类做单类检测。4.4 现象验证集 mAP 高但实际推理漏检小目标原因imgsz640下远景拐杖只有十几个像素下采样后特征几乎消失。验证集里如果小目标少指标会虚高。解决统计标注框的宽高分布如果大量框小于 32 像素把imgsz提到 960 或 1280同时开mosaic1.0和scale0.5增强小目标。推理时用yolo detect predict imgsz960保持一致。4.5 现象训练到 60 轮后验证指标突然崩掉原因学习率没退火或者close_mosaic设置太晚mosaic 增强在后期干扰了收敛。解决YOLOv8 默认最后 10 轮关闭 mosaic如果自定义了close_mosaic确保它小于总 epoch 的 10%。另外加cos_lrTrue让学习率余弦退火崩点会明显减少。5. 从能跑到好用二类检测的验证技巧与一个提点习惯训练跑通只是及格线真正决定这个数据集值不值得投入的是你能不能快速判断模型在真实场景里的边界。我一般会做两件事一是用yolo detect val导出每张验证图的预测结果按mAP从低到高排序专门看最差的那 20 张通常能发现标注错误或场景偏差二是拿手机在楼道、地铁口拍 30 张没见过的图手动跑推理看漏检和误检集中在哪。验证时有个具体技巧把conf阈值从默认 0.25 调到 0.4 再跑一遍验证。二类任务里拐杖和栏杆、雨伞的相似度高低阈值会引入大量假阳性。如果 0.4 下召回掉得不多但精确率明显上升说明模型学到的特征是可用的只是决策边界需要收紧。反过来如果 0.4 下召回暴跌说明模型对拐杖的特征抓得不够得回去补样本或加分辨率。验证项推荐命令/操作判断标准整体指标yolo detect val data... imgsz640mAP50 0.85 可用最差样本按 mAP 排序看低分图检查是否标注错误阈值敏感度conf 从 0.25 调到 0.4精确率升、召回降幅 10%真实场景手机拍 30 张跑推理漏检集中在远景则提 imgsz最后说个我自己的习惯每次训完二类检测我都会把confusion_matrix.png和val_batch0_pred.jpg存到一个固定文件夹命名带上日期和imgsz。因为二类任务的坑往往不是模型结构而是标注和场景分布隔一周回头看这些图比翻训练日志快得多。4635 张不算多但只要你把 VOC 和 YOLO 对齐、把类别共现理清、把验证阈值调对它足够撑起一个能落地的导盲犬与拐杖检测基线。希望帮到你。本文还有配套的精品资源点击获取
觉得有用,分享给同行:

为您的企业打造数字门面

稳重轻奢商务风格,端正雅致视觉,长效耐看不易过时。

立即咨询 →