简介泊车位目标检测是自动驾驶与智慧停车场景中的常见任务这套数据集面向需要训练YOLO系列模型的开发者与课程学员提供1000张真实场景图片并使用LabelImg完成高质量标注。标签同时包含VOC的xml、COCO的json和YOLO的txt三种格式分别存放可直接接入主流检测框架省去格式转换环节。包内共2000个文件除标注文件外还搭配3个Python划分脚本可灵活生成训练集、验证集和测试集6个HTML教程覆盖Linux与Windows环境下的YOLO搭建、训练案例修改另含1个yaml配置方便快速复现。整个压缩包约238.49MB结构清晰适合入门到进阶使用。目前已有507人学习下载配套博文中还提供了详情展示与更多数据集获取方式对于正在做毕业设计、课程项目或竞赛准备的用户这是一份即拿即用的实操型资料。若有其他类别或数量需求也可联系博主进一步沟通。1. YOLO泊车位目标检测数据集真实场景下的1000张与三格式标签泊车位检测这个任务数据比模型更值钱。很多开源停车场数据集要么是俯视拍摄要么场地干净得不像真实环境模型训练完一上实际道路就翻车。这套YOLO泊车位目标检测数据集是1000张真实场景图片用LabelImg逐张标注同时产出VOC(xml)、COCO(json)、YOLO(txt)三套标签直接省掉格式转换的麻烦。适合正在做YOLO系列目标检测落地、需要一套能直接喂给训练脚本的数据源或者刚入门想完整走一遍“标注理解 → 数据划分 → 环境搭建 → 模型训练”全流程的从业者。2. 三种标注格式的差异与选择看懂XML、JSON和TXT2.1 先看目录结构拿到压缩包第一时间确认的事解压rar之后先别急着看那堆HTML教程直接扫一眼数据文件夹的层次。这个数据集把三种格式标签分开放置常见的组织方式是dataset/ ├── VOC/ │ ├── Annotations/ # 存放xml标签 │ └── JPEGImages/ # 存放jpg图片 ├── COCO/ │ ├── annotations/ # 存放json标签 │ └── images/ # 存放jpg图片 ├── YOLO/ │ ├── labels/ # 存放txt标签 │ └── images/ # 存放jpg图片 └── scripts/ # 三个划分脚本及说明这里有一个关键信息三个文件夹里放的是同一批图片只是标签表示方法不同不是三批数据。我见过有人以为数据集总共有3000张其实就是1000张图配了三套标签。目录结构本身也暗示了使用方式——你用YOLOv5/YOLOv8训练路径直接指到YOLO/images你要跑Faster R-CNN或MMDetection就指到VOC或COCO。这种按框架区分目录的做法比把所有标签丢进一个文件夹里方便得多缺点是如果你自己写数据加载器需要同时考虑三个目录的路径拼接容易混淆。2.2 VOC格式XML标签逐字段拆解VOC格式是早期目标检测最通用的格式每张图片对应一个同名的XML文件。用文本编辑器打开Annotations下的任意文件结构大致是annotation folderJPEGImages/folder filenameparking_001.jpg/filename size width1920/width height1080/height depth3/depth /size object nameparking_space/name poseUnspecified/pose truncated0/truncated difficult0/difficult bndbox xmin320/xmin ymin180/ymin xmax860/xmax ymax540/ymax /bndbox /object /annotation几个字段需要拆开讲。filename必须和JPEGImages目录下的实际文件名完全一致大小写和扩展名都不能差否则训练时加载器按文件名索引会找不到图片。name是类别名这套数据里统一是parking_space单类检测任务最大的优势就是类别数少模型复杂度可以做得很低。bndbox里存的是绝对像素坐标xmin/ymin是左上角xmax/ymax是右下角。这里最常见的理解偏差是认为xmax/ymax是框的宽和高实际不是换算宽高需要自己做减法。另外difficult字段表示这个目标是否难以识别默认是0但如果你在原始XML里看到1注意有些训练框架会把difficult1的样本自动过滤掉这直接影响最终训练样本数量。2.3 COCO格式JSON的categories与annotations对应关系COCO格式是把所有图片的标注汇总到一个JSON文件里运行任何训练脚本前必须搞懂三个顶层字段的关联。一个标准的标注JSON长这样{ images: [ { id: 1, file_name: parking_001.jpg, width: 1920, height: 1080 } ], annotations: [ { id: 1, image_id: 1, category_id: 1, bbox: [320, 180, 540, 360], area: 194400, segmentation: [], iscrowd: 0 } ], categories: [ { id: 1, name: parking_space } ] }最容易翻车的点集中在bbox字段。COCO的bbox是[x, y, width, height]而VOC是[xmin, ymin, xmax, ymax]两者不是直接替换关系需要转换。area虽然是辅助字段但有些评估脚本会校验这个值是否等于width * height不匹配时mAP计算会出问题。category_id从1开始通过categories数组里的id和name映射到具体类别。注意不是按照数组下标来对应而是按id值对应如果一张图里有多个类别标注里的category_id必须和categories里的完全匹配。很多人用脚本做VOC转COCO时只转换了坐标忘了重新生成category_id导致训练时所有框的类别都错。2.4 YOLO格式归一化坐标的计算与校验YOLO格式每个txt文件对应一张图片每行一个目标。数据集的YOLO/labels目录下就能看到类似内容0 0.3098958333333333 0.3333333333333333 0.4479166666666667 0.3333333333333333这行五个数分别是class_id、x_center、y_center、width、height全部是归一化到01之间的浮点数。归一化坐标的计算方式如下x_center (xmin xmax) / 2 / image_width y_center (ymin ymax) / 2 / image_height width (xmax - xmin) / image_width height (ymax - ymin) / image_height这里有个血泪经验归一化坐标和图片尺寸强绑定。如果你训练前对图片做了resize或裁剪txt里的数值就全部失效必须重新换算。另外class_id是从0开始编号的而VOC的name是字符串两者之间的对应关系靠一个类别文件来维护YOLOv5里叫data.yamlYOLOv8里也是顺序错一个模型检测出来的框就全部张冠李戴。拿到txt标签后建议先跑一遍校验确认坐标范围在01之间class_id没有超出类别总数awk {if($20||$21||$30||$31||$40||$41||$50||$51) print $0} YOLO/labels/*.txt如果这个awk命令有输出说明存在非法标注需要返回LabelImg重新修正。2.5 三种格式的适用框架与转换思路格式典型加载框架适用场景VOCFaster R-CNN、SSD、MMDetection早期配置走VOC式训练流程COCOMMDetection系列、Detectron2需要COCO评估指标YOLOYOLOv5/YOLOv8/YOLOv11常规训练直接用官方仓库训练转换的核心思路是坐标体系从VOC的左上/右下像素坐标到COCO的左上像素宽高再到YOLO的中心点归一化宽高。三套格式的类别信息也要保证同序。这个数据集把三种格式都准备好了省去的是最无聊的转换环节把精力放在后面真正影响模型效果的环节上。3. 划分脚本实战从原始数据到训练集/验证集/测试集3.1 三个脚本的区别先选对再运行这个资源包里最实用的部分除了数据本身就是三个划分脚本。很多模型训练项目死得不明不白根本原因不是模型结构而是训练集和验证集划分方式有问题。三个脚本应对三种不同需求脚本名称功能适用场景训练集、验证集、测试集划分脚本图片标签划分写入新文件夹.py按比例生成三个新文件夹复制图片和标签需要严谨的测试集做最终评估训练集、验证集划分脚本图片标签划分写入新文件夹.py只生成train和val两个文件夹快速训练调试不追求最终测试指标split_train_val生成ImageSets下txt文件划分脚本.py生成ImageSets/Main下的txt文件不移动文件兼容VOC系列加载器不想复制数据选脚本的逻辑很直接如果打算用YOLOv5/v8这种自带数据划分机制的训练框架用第二个脚本就够了训练时在data.yaml里指定train和val路径框架内部会做比例控制。如果用的是VOC老流程或者要在别的框架自定义数据加载用第三个脚本生成txt索引文件不会破坏原有文件结构处理大文件时也更省磁盘。3.2 图片和标签一起划分脚本核心逻辑与参数解释以“训练集、验证集、测试集划分脚本”为例它的核心逻辑是读取图片文件名列表按比例切分三个子集然后同时复制图片和对应的标签到新目录。这里截取关键代码段做解释import os import random import shutil # 配置区 img_dir YOLO/images # 原始图片目录 label_dir YOLO/labels # 原始标签目录 target_dir dataset_split # 输出根目录 train_ratio 0.8 # 训练集比例 val_ratio 0.1 # 验证集比例 # 读取全部图片列表打乱顺序 img_files [f for f in os.listdir(img_dir) if f.endswith(.jpg)] random.seed(42) random.shuffle(img_files) # 按下标切分 train_files img_files[:int(len(img_files) * train_ratio)] val_files img_files[int(len(img_files) * train_ratio): int(len(img_files) * (train_ratio val_ratio))] test_files img_files[int(len(img_files) * (train_ratio val_ratio)):] # 复制图片和标签到各自分区目录 for split, files in [(train, train_files), (val, val_files), (test, test_files)]: os.makedirs(os.path.join(target_dir, split, images), exist_okTrue) os.makedirs(os.path.join(target_dir, split, labels), exist_okTrue) for img in files: shutil.copy(os.path.join(img_dir, img), os.path.join(target_dir, split, images, img)) label img.replace(.jpg, .txt) if os.path.exists(os.path.join(label_dir, label)): shutil.copy(os.path.join(label_dir, label), os.path.join(target_dir, split, labels, label))代码逻辑不复杂但有几个参数值得说清楚。train_ratio0.8意味着800张训练图val_ratio0.1是100张验证图剩余100张自动归入测试集这个比例对于1000张的数据量来说比较合理。random.seed(42)是给随机数生成器装一个固定种子保证每次运行脚本划分结果一致——很多人划完分前后两次训练用的训练集不一样排查半天找不到原因其实就是没固定种子。脚本用shutil.copy复制而不是os.rename移动这个细节很重要。复制能保留原始数据划分完如果发现训练效果不对想重新划分原始文件还在如果直接移动划分一次就永久改变了数据分布没有后悔药。3.3 生成ImageSets下txt的脚本兼容VOC训练流程第三个脚本的逻辑完全不同它不复制任何文件而是在ImageSets/Main下生成文本索引文件。运行方式python split_train_val生成ImageSets下txt文件划分脚本.py --data VOC --ratio 0.8 0.1 0.1生成的train.txt内容如下parking_001 parking_002 parking_003 ...每行是图片文件名去掉.jpg后的“stem”不包含目录路径也不带扩展名。VOC系列数据加载器拿到train.txt后会自动去JPEGImages/{stem}.jpg找图片去Annotations/{stem}.xml找标签。这种设计的好处是加载路径集中在一个txt里坏处是如果你动了目录结构所有索引全部失效。使用这类脚本时先确认--data VOC指向的目录下确实有Annotations和JPEGImages这两个子目录而不是嵌套了一层。常见的翻车现场是数据集解压后是VOC/VOC2007/Annotations这种深层次结构脚本按VOC/Annotations找文件直接报目录不存在。3.4 划分完成后的目录检查清单不管用哪种方式完成划分训练前一定要做一次目录体检。我的习惯是按这个顺序检查# 统计每个目录下的图片数量和标签数量 find dataset_split/train/images -name *.jpg | wc -l find dataset_split/train/labels -name *.txt | wc -l # 抽查标签是否和图片同名 ls dataset_split/train/images/ | sed s/.jpg// /tmp/img_list ls dataset_split/train/labels/ | sed s/.txt// /tmp/lab_list diff /tmp/img_list /tmp/lab_list | head -20第一个命令验证图片数量是否符合比例第二个验证标签和图片名是否一一对应。如果diff有输出说明存在有图无标签或有标签无图的情况需要返工。这一步虽然枯燥但能避免训练到一半才报错说找不到标注文件那时候已经浪费了几个小时。4. 环境搭建与训练Linux和Windows两套流程4.1 Linux环境搭建从Ubuntu系统到YOLO依赖资源包里预装了Linux和Windows两套环境的教程这部分是给正在准备训练环境的人走的。Linux端的完整流程围绕四步展开装Ubuntu → 装NVIDIA驱动和CUDA → 创建conda环境 → 安装PyTorch和YOLO依赖。# 安装系统基础依赖 sudo apt update sudo apt install -y build-essential git python3-pip # 创建conda环境指定Python 3.8保证兼容性 conda create -n yolo python3.8 -y conda activate yolo # 安装PyTorch注意CUDA版本必须匹配 pip install torch1.13.1 torchvision0.14.1 --index-url https://download.pytorch.org/whl/cu117 # 克隆YOLOv5仓库并安装依赖 git clone https://github.com/ultralytics/yolov5 cd yolov5 pip install -r requirements.txt这里的版本组合是有讲究的。PyTorch 1.13.1配合CUDA 11.7是我踩坑后固定下来的一套稳定组合兼容性好遇到算子报错概率低。如果机器显存比较新、驱动版本高直接装CUDA 12.x配最新PyTorch也没问题但这时最好同步用YOLOv8或更新的版本因为老版本YOLO的某些C算子在新CUDA下需要重新编译。一个常见的装包错误是漏了--index-url参数系统默认从官方源装CPU版PyTorch训练时检测不到GPU速度慢到没法用。装完后用python -c import torch; print(torch.cuda.is_available())验证输出True才说明CUDA打通了。4.2 Windows环境搭建路径与CUDA的兼容性Windows端教程面向的是单机调试场景。相比LinuxWindows端的坑集中在两个地方CUDA版本匹配和路径分隔符。操作顺序不复杂先装NVIDIA显卡驱动然后装CUDA Toolkit版本以驱动支持的最高CUDA版本为准创建conda环境并安装PyTorch选版本时要知道自己显卡算力和CUDA版本再明确对应的pip安装命令克隆YOLOv5或者直接下载release包把项目路径里的反斜杠和正斜杠统一改成/很多Windows下训练报FileNotFoundError就是路径分隔符搞的鬼另一个Windows特有的问题是杀毒软件会拦截pip安装写权限导致依赖装到一半就报错。我一般会先把conda环境和项目目录加入白名单再执行安装命令能省不少事。如果你在Windows上训练特别慢先检查有没有开节能模式NVIDIA显卡在电池模式下会降频训练速度直接减半。4.3 修改配置训练自己的数据集data.yaml与超参所谓“根据案例修改训练自己的数据集”核心就是改data.yaml和训练命令。以YOLOv5为例data.yaml需要改写为# data.yaml train: dataset_split/train/images val: dataset_split/val/images test: dataset_split/test/images nc: 1 names: [parking_space]这份配置文件告诉训练器三件事训练集图片在哪里、验证集在哪里、要识别几个类别以及类别叫什么。nc和names必须和标签里的class_id对应上。标签中class_id为0那么names列表里第0个位置就必须是parking_space顺序错位是最隐蔽的坑。训练启动命令python train.py --data data.yaml --weights yolov5s.pt --epochs 100 --batch-size 16 --imgsz 640参数选择有实际依据。--weights yolov5s.pt是基于预训练权重微调对于1000张数据的体量从零开始训练很容易过拟合预训练权重提供的底层特征能显著加速收敛。--epochs 100在这个数据量下足够观察到明显的loss下降趋势如果100轮后mAP还在持续上升可以加跑50轮。--batch-size按照显存容量调整6GB显存建议16以下8GB以上可以尝试32。训练过程中留意两个输出位置runs/train/exp/下的results.csv记录了每个epoch的metrics可以拿来做实时曲线分析权重文件存放在weights/目录其中best.pt是验证集上表现最好的模型last.pt是最后一轮的模型。做最终评估用best.pt继续训练用last.pt。4.4 训练完成的首次推理验证训练完成后用一张未参与训练的测试集图片做推理验证模型真实表现python detect.py --weights runs/train/exp/weights/best.pt \ --source dataset_split/test/images/parking_035.jpg \ --conf-thres 0.35 --imgsz 640--conf-thres 0.35是一个比较实用的置信度阈值。停车位检测场景里误检代价通常高于漏检0.35-0.4之间能过滤掉大多数低置信度的假阳性框。如果检测结果里同一个车位出现多个重叠框说明NMS阈值可能偏低可以通过--iou-thres适当调高。第一次推理建议打开输出的标注图片把检测框和原图对照着看比只看数字指标更能发现标注质量和模型偏向的问题。5. 常见问题排查标注、划分、训练三个环节的坑5.1 标签和图片数量对不上现象训练时控制台报错found 0 images in train path或者AssertionError: train set not found。 原因最常见的是划分脚本执行过程中标签名和图片名不匹配导致部分标签没有被复制。比如图片是parking_001.jpg标签却命名成了parking_1.txt按扩展名替换的逻辑就会漏掉。 解决统一文件名格式。用批量重命名把标签名称对齐图片名称或者重跑划分脚本前先在原始数据目录里执行ls images/ | sed s/.jpg// /tmp/img_list ls labels/ | sed s/.txt// /tmp/lab_list diff /tmp/img_list /tmp/lab_list输出结果里多出来的行就是要处理的文件。对齐之后重跑划分脚本多数情况下问题即解决。5.2 训练时Loss不下降或剧烈波动现象训练跑了30个epochloss曲线一直在1.52.5之间反复震荡完全没有收敛趋势。 原因两类情况。一是学习率过大导致参数更新跨度过大在最优值附近来回弹跳二是训练数据里存在大量错标框模型每次收敛都被错误样本打断。 解决先把学习率降到0.0005观察2个epoch如果曲线变稳定但依然不下降基本可以断定是标注质量问题。打开YOLO/labels下的txt文件和图片做对应检查重点看那些明显标错的框——比如框住整面墙而不是车位线、漏标了角落的车位。错误标注比例超过5%就需要用脚本清洗不要抱有侥幸心理。5.3 class_id和类别名称错位现象模型能检测出目标可视化时所有框上的类别名都不对或者出现训练时根本没有见过的类别名。 原因txt标签里的class_id和训练配置data.yaml里的names顺序不一致。假设标签里写的是0但names列表第0个位置是car实际数据标的是parking_space最终可视化就会错位。 解决先统一标签体系。用命令快速统计训练集中的类别id分布awk {print $1} dataset_split/train/labels/*.txt | sort | uniq -c如果输出只有0这个数字说明类别id只有0号如果出现大于等于1的数字说明部分标注使用了其他id需要回到标注工具修正。确认id分布后再对照data.yaml里的names列表保证顺序完全一致。5.4 验证集表现好但测试集崩现象训练过程中val上的mAP稳步上升但测试集上实测检测效果很差漏检非常严重。 原因数据划分时没有固定随机种子每次运行划分脚本得到的训练集和验证集都不同导致最终使用的训练集可能和模型训练时的分布不一致。更隐蔽的情况是数据集中存在重复图片——同一场景的多角度拍摄被当作了多张独立图片这些图像同时出现在训练集和验证集里验证集指标虚高。 解决划分脚本必须固定random.seed保证每次执行结果一致。同时建议对原始图片做一次去重md5sum images/*.jpg | sort | awk {print $1} | uniq -d有重复hash输出的图片需要手动清理再去重跑划分脚本。5.5 训练中途OOM与显存不足现象训练到某个epoch控制台直接弹出CUDA out of memory进程被杀前面几个小时的训练全部白费。 原因batch_size设置过大或者开启了--cache参数把整个数据集预加载到显存。1000张640分辨率的图片全量缓存大约需要4-6GB显存加上模型参数和中间激活值小显存显卡根本扛不住。 解决先把batch_size降到4--workers降到2再试跑10个epoch确认稳定性。如果依然OOM就把--imgsz降到416检测精度降低但对泊车位这类目标来说完全够用。记住一个原则训练时间是宝贵的数据加载慢一点可以接受训练中途进程被杀才是真正的灾难。6. 验证结果与进阶用法mAP可视化与ONNX导出训练结束后不要只看loss曲线真正的性能评估要看验证集指标和可视化结果。YOLO训练过程自动生成的runs/train/exp/目录里有几个文件值得重点关注val_batch0_pred.jpg展示验证集图片的预测框可视化confusion_matrix.png展示目标分类的混淆矩阵results.csv记录了每个epoch的所有指标变化曲线。其中PR_curve.png反映的是置信度阈值从高到底变化时Precision和Recall的权衡曲线。曲线整体越贴近右上角模型越可靠。如果你看到曲线在置信度0.3-0.5区间突然掉头向下说明模型对困难样本的处理不够好可以尝试调低--conf-thres观察。对部署场景而言训练出的best.pt直接跑PyTorch推理不够高效建议导出为ONNX格式python export.py --weights runs/train/exp/weights/best.pt --include onnx --img-size 640ONNX模型在Jetson系列、树莓派或者普通的边缘盒子设备上都能获得比PyTorch原生推理快量级的性能且不依赖完整的torch环境。导出完成后可以先用onnxruntime做一个快速推理测试确保输出的检测框坐标和置信度与PyTorch版本一致。在那以后我每次拿到新数据集都强制走一遍固定流程确认目录与标签格式 → 可视化抽查标注质量 → 固定种子划分数据 → 预训练权重起步训练 → 看PR曲线和混淆矩阵 → 导出ONNX做部署验证。这套循环下来数据集本身的价值才能落到实际业务效果上。希望帮到你。本文还有配套的精品资源点击获取