夜间行人检测数据集与YOLO11三平台训练全流程解析

发布时间:2026/9/17 4:31:03
夜间行人检测数据集与YOLO11三平台训练全流程解析 简介资源面向夜间与低光环境中的行人检测任务整理自真实场景共五千张高质量图片覆盖夜间街景、夜间道路、遮挡行人、严重遮挡行人等典型情况适合公共场所监控场景下的夜间行人检测项目也可作为通用行人检测数据集在夜间样本上的重要补充。标注由LabelImg完成质量较高并同时提供VOC(xml)、COCO(json)、YOLO(txt)三种常用格式下载后无需转换即可直接用于YOLO等主流算法训练。随包还附赠YOLO11一键训练脚本支持GPU(GPUs)、CPU、Mac(M芯片)多平台运行同时提供博主训练结果日志便于复现与对比调参。资源本体较大故以单个PDF形式提供约6.07MBPDF内包含完整的数据集介绍、缩略图、LabelImg标注截图及百度网盘获取方式目前已有610人学习/下载适合正在开展夜间行人检测项目或需要扩充低光样本的研究者和开发者。1. 夜间行人检测5000 张标注图背后的三个硬问题白天训练好的 YOLO 模型晚上在监控画面里经常漏检一半以上这是做安防项目的同行最容易撞上的状况。夜间行人目标的亮度低、纹理弱路灯造成的局部过曝和人车遮挡又会把特征进一步破坏拿白天数据训出来的模型几乎不可用。这套夜间行人目标检测数据集包含 5000 张真实场景图片覆盖夜间街景行人、夜间道路行人、夜间遮挡行人、严重遮挡行人四类场景全部由 labelimg 人工标注同时提供 VOC(xml)、COCO(json)、YOLO(txt) 三种目标检测数据集格式可以直接喂给 YOLO 系算法训练。配套的 YOLO11 一键训练脚本覆盖 GPU、CPU、Mac(M 芯片) 三种运行环境从数据读取到权重导出一步到位还附带训练结果日志可以对照。适合正在做公共场所监控目标检测、或者要给现有行人检测模型补充夜间场景数据的项目直接用。2. 从 labelimg 到三种格式VOC / COCO / YOLO 坐标体系与转换细节2.1 数据集构成与标注质量5000 张图并不是同一个场景的连续帧截取整体场景覆盖了夜间街景、夜间道路、夜间遮挡行人、夜间严重遮挡行人四类。这里“严重遮挡”的定义是行人身体超过 1/3 被其他物体或行人盖住这类样本在监控场景里非常常见也是公开白天数据集里最缺的部分。标注用的是 labelimg它是本地标注工具输出的是 PASCAL VOC 格式的 xml 文件每个 xml 与一张 jpg 同名放在同一目录下。labelimg 标注时是人工拉框所以在严重遮挡的场景里框的边界会贴着可见部分切这是后续做格式转换时需要注意的一个点可见部分框和完整身体框的语义不一样训练时模型学到的是“框住可见区域”这个规则。数据集同时提供了三种格式说明 xml、json、txt 是已经转换好并且校验过的。实际项目中从零标注时要自己处理转换。下面的转换脚本就是基于这种数据组织方式写的做一次转换、做一次校验能省掉后面排错的好几天时间。2.2 三种格式的坐标系统差异三种格式的核心差别在两点坐标表达方式以及归一化方式。VOC xml 中每个目标用一个 object 节点描述框坐标是 bndbox 下的四个值object nameperson/name bndbox xmin320/xmin ymin240/ymin xmax640/xmax ymax720/ymax /bndbox /objectxmin、ymin、xmax、ymax 都是相对于原图的像素坐标左上角为原点单位为像素。COCO json 的 annotations 里的 bbox 是[x, y, width, height]即左上角坐标加宽度、高度同样是像素单位。区别在于 COCO 格式要求 image_id 关联还要有 area 和 iscrowd 字段。很多人在转换时只处理 bbox漏了 area 和 image_id 的映射数据集放到 pycocotools 里评估时会直接报错。YOLO txt 每行是一个目标的标注格式是class_id cx cy w h其中 cx、cy 是归一化到 [0,1] 的中心点坐标w、h 是归一化宽高。这个坐标体系可以直接被 YOLO 系列模型读取不需要额外做数据集准备。三者之间的转换要抓住两个操作一是把 VOC 的 xmin/ymin/xmax/ymax 换算成中心点加宽高二是把像素值除以图片宽高变成归一化值。2.3 格式转换与一致性校验下面这段代码处理 VOC 转 YOLO这是实际项目里最常用的转换路径import os import xml.etree.ElementTree as ET CLASS_NAMES [person] # 与 data.yaml 中的 names 保持一致 def voc_to_yolo(xml_path, img_w, img_h): tree ET.parse(xml_path) root tree.getroot() lines [] for obj in root.iter(object): name obj.find(name).text if name not in CLASS_NAMES: continue cls_id CLASS_NAMES.index(name) box obj.find(bndbox) xmin float(box.find(xmin).text) ymin float(box.find(ymin).text) xmax float(box.find(xmax).text) ymax float(box.find(ymax).text) # 边界约束防止标注框越界造成归一化值超出 [0,1] xmin max(0, xmin) ymin max(0, ymin) xmax min(img_w, xmax) ymax min(img_h, ymax) cx (xmin xmax) / 2.0 / img_w cy (ymin ymax) / 2.0 / img_h w (xmax - xmin) / img_w h (ymax - ymin) / img_h lines.append(f{cls_id} {cx:.6f} {cy:.6f} {w:.6f} {h:.6f}) return lines for xml_file in os.listdir(annotations): if not xml_file.endswith(.xml): continue xml_path os.path.join(annotations, xml_file) # 实际项目中应从 xml 的 size 节点读取图片宽高这里用固定值演示 lines voc_to_yolo(xml_path, 1920, 1080) txt_path os.path.join(labels, xml_file.replace(.xml, .txt)) with open(txt_path, w) as f: f.write(\n.join(lines))代码里做了两件容易忽略的事一是越界裁剪labelimg 偶尔会拉出超出画幅的框特别是在快速标注时二是类别过滤把不参与训练的类别直接跳过。cx、cy、w、h 都除以图片宽高这样无论输入分辨率是多少标注信息都能映射到 [0,1] 区间。如果直接复用别人写的转换脚本注意确认图片尺寸是读取的 xml 里size节点而不是写死的 1920x1080否则训练时标签全部错位。转换完要做一次校验检查每个 txt 是否为空、每个坐标值是否在 [0,1] 内、每行第一个数字是否越界。一个常见的坑是 classes 顺序不一致VOC 里 name 是字符串YOLO 里是整数索引训练时 data.yaml 里的 names 顺序必须与转换时 CLASS_NAMES 的顺序完全一致否则模型会学到颠倒的语义。COCO 转 YOLO 时同理categories 的 id 与索引位置要一一对应。这个数据集直接给出了三种格式省去了自己转换的步骤但理解这个转换逻辑对排查训练时“检测出目标但类别错乱”这类问题很有帮助。下一章进入 YOLO11 训练环节。3. YOLO11 三平台一键训练data.yaml 到 CUDA / MPS / CPU 的适配3.1 data.yaml 与目录组织YOLO11 使用 Ultralytics 框架训练的第一步是准备 data.yaml。这个文件告诉模型三件事训练集路径、验证集路径、类别名称表。对单类行人检测配置如下path: ./night_person train: images/train val: images/val names: 0: personpath 是数据集根目录相对路径train 和 val 可以写成绝对路径也可以基于 path 拼接。names 的索引必须和第 2 章 YOLO txt 里的 class_id 对齐。这里只有一个 person 类索引是 0。很多人在多类数据集中把 names 顺序和转换脚本里的 CLASS_NAMES 搞混导致类别错乱这个细节值得反复检查。3.2 训练脚本中的平台判断“一键训练”的核心逻辑不在 YOLO11 本身而在于根据运行环境自动选择 device。PyTorch 的推理后端有三个分支CUDA、MPS、CPU。MPS 是 Apple Silicon 上 PyTorch 的 GPU 加速后端对应 Mac M 系列芯片。判断顺序很关键因为 MPS 在部分 Linux 环境下可能被误判要先查 CUDA 再查 MPSimport torch from ultralytics import YOLO def auto_select_device(): if torch.cuda.is_available(): return 0 # 单卡训练多卡可写 0,1 if hasattr(torch.backends, mps) and torch.backends.mps.is_available(): return mps # Mac M 芯片 return cpu if __name__ __main__: device auto_select_device() model YOLO(yolo11n.pt) # 预训练权重n/s/m/l/x 可选 results model.train( datadata.yaml, epochs120, imgsz640, batch16 if device ! cpu else 8, lr00.01, devicedevice, workers4 if device ! cpu else 0, projectruns/detect, namenight_person, exist_okTrue, )device 传字符串 0 表示使用第一张显卡mps 使用 Mac 的 GPU 后端cpu 则退回纯 CPU。batch 在 CPU 环境下要调小因为单次前向的显存约束变成内存约束workers 在 CPU/MPS 下也建议设为 0避免 DataLoader 多进程和 MPS 内存分配器冲突。PyTorch 的 MPS 后端在 macOS 12.3 之后才完整可用Ultralytics 版本最好固定在 8.2 以上否则部分算子的 MPS 实现会回退到 CPU训练速度反而不如直接用 CPU。数据加载器在 Windows 上还容易遇到 spawn 相关报错常见做法是把训练代码放进if __name__ __main__:保护块里Windows 下多进程数据加载时不会无限递归创建子进程。脚本里保留这个判断是稳定性的第一道保障。3.3 平台适配参考与训练日志解读三个平台的参数配置可以按这张表来定起点平台device 值batchimgsz备注NVIDIA GPU (8~12GB)016~3264012GB 显存可试 32OOM 就减半Mac M 系列 (MPS)mps8~16640建议 batch 从 8 起步CPU (无 GPU)cpu4~8480降低分辨率换取可接受的训练时间GPU 显存不够时不要只把 batch 调小还可以在 train 参数里加cacheFalse避免把整图缓存到显存或者用ampTrue混合精度训练。MPS 环境下 AMP 支持不如 CUDA 稳定遇到 NaN 损失时优先关掉 AMP 再排查。训练日志主要盯三组指标train/box_loss、train/cls_loss 和 val 上的 mAP50。前 20 个 epoch 里 box_loss 会从 1.5 附近快速下降然后进入平台期mAP50 在前 30 个 epoch 通常能到 0.5 左右如果 50 个 epoch 后 mAP50 还在 0.2 以下说明数据集划分、标注格式或 data.yaml 里的类别配置有问题不是训练轮数不够。博主提供的训练结果日志可以直接对照重点看第 50 和第 100 epoch 两个节点的指标避免在自己环境上重复踩坑。4. 夜间场景收敛调优从 baseline 到低光增强与遮挡处理4.1 baseline 参数与改进方向第一版训练直接用第 3 章的参数即可得到 baseline。夜间行人检测有特殊性在 baseline 基础上通常要调整三组参数输入分辨率、数据增强、损失权重。输入分辨率方面夜间小目标多远处行人可能只有 40x80 像素的大小imgsz 从 640 提到 960 能直接涨 2~4 个点 mAP50代价是训练时间增加约 1.5 倍。如果显存放不下 960可以用rectTrue让模型按批次内最长边做矩形推理而不是把所有图都填充到 960。数据集里的夜间街景图片多数是 1080p 监控画面截帧分辨率充足模型输入成了瓶颈。数据增强方面YOLO11 的默认增强覆盖了 mosaic、hsv 扰动、随机翻转等但对夜间场景还能加一层偏置# hyp.night.yaml覆盖默认超参 hsv_h: 0.015 hsv_s: 0.5 hsv_v: 0.6 degrees: 5.0 translate: 0.1 scale: 0.5 mosaic: 0.8 mixup: 0.1hsv_v 从默认 0.4 提到 0.6是因为夜间场景亮度方差大路灯直射区域和阴影区域之间的亮度差可以超过 10 倍把亮度扰动加大能让模型对光照变化更鲁棒。mosaic 降到 0.8是为了保留夜间整图的上下文——mosaic 拼图会破坏画面整体亮度的统计特性夜间数据如果不降低 mosaic 概率模型容易学到“图片变暗即行人”这种错误映射。mixup 保持 0.1 低水平即可混合样本在目标重叠密度高的夜间场景里容易产生语义混淆。4.2 严重遮挡样本的处理策略数据集里包含了严重遮挡行人这部分样本在 val 集上的表现往往是最差的。常规做法是检查混淆矩阵中漏检的样本大多数漏检发生在两个行人几乎重叠、标注框 IoU 超过 0.7 的情况下。此时 YOLO 的 NMS 会抑制掉置信度较低的那个框。针对这个问题有两个思路一是训练时把后处理相关参数放宽让模型在 NMS 前输出更多候选框二是在推理阶段把iou0.45调高到iou0.7减少重叠框被误抑制的概率。这里要注意提高 IoU 阈值会增加重复框所以还要配合max_det限制最大输出数量。更可靠的做法是用 BoT-SORT 或 ByteTrack 做视频流的跟踪关联用时间维度的连续信息来维持严重遮挡行人的 ID而不是在单帧上追求接近上限的召回。博主提供的一键训练脚本里没有带跟踪模块但推理阶段接一个 ByteTrack 的成本很低夜间行人检测最终落在监控场景时基本都会走到这一步。4.3 训练异常排查训练中最常见的异常是 loss 变成 NaN。在 MPS 平台先关 AMP 再重训在 CUDA 平台先检查 lr0 是否过大0.01 在单卡小 batch 下正常但如果数据噪声大降到 0.005 更稳妥。另一个易踩的坑是标注框本身就存在问题——如果某个 txt 行内坐标计算出负值或 0 宽度损失函数会算出异常梯度表现为训练几轮后 val mAP 突然归零。用下面这条命令可以快速扫出异常标注文件find labels -name *.txt -size 0 -delete awk -F { for (i2; iNF; i) { if ($i 0 || $i 1) { print FILENAME; break } } } labels/*.txt第一条命令删除空标注文件第二条找坐标越界的文件。空标注文件在 COCO 格式里对应“图片存在但没有目标”的情况保留会造成训练时该图片无标签而报错越界标注则直接影响损失计算。这份数据集的作者已经处理过这些问题但如果你是拿其他来源的夜间数据自己标注这两条命令要养成习惯。白天预训练权重在夜间数据上会有一个适应期。用 yolo11n.pt 做初始化时前 10 个 epoch 的 val mAP50 可能会低于随机初始化这是特征空间在向夜间分布偏移的正常现象不要中途停训。如果数据集和白天场景差异太大可以冻结前 10 层只训练检测头等损失稳定后再解冻全部层。YOLO11 在 Ultralytics 框架里可以通过model.model.model[:10].requires_grad_(False)这种方式冻结指定层实现也不复杂。5. 验证与部署评估脚本、置信度调整和导出5.1 用验证集输出混淆矩阵与 mAP训练完的模型用 Ultralytics 自带的 val 接口评估yolo detect val modelruns/detect/night_person/weights/best.pt datadata.yaml imgsz640 conf0.25 iou0.5评估结果里重点看三类指标mAP50、mAP50-95、每类别的混淆矩阵。mAP50 反映“框是否大致框准”mAP50-95 才反映定位精度。夜间行人在 mAP75 段通常会比 mAP50 低 15 个点以上这是因为遮挡样本的标注框边界难以精确贴合可见区域定位误差被放大。如果只需要监控场景的计数和区域入侵报警mAP50 达到 0.7 就够用如果要做人的朝向或姿态判断需要把 mAP50-95 也拉起来这通常要配合更高分辨率的输入和更精细的标注。5.2 推理阶段的可视化与部署夜间监控视频流推理可以直接跑下面这段from ultralytics import YOLO model YOLO(runs/detect/night_person/weights/best.pt) results model.predict( sourcecamera_12.mp4, conf0.35, iou0.7, imgsz640, saveTrue, projectoutput, namenight_detect, device0, ) for r in results: boxes r.boxes counts sum(1 for box in boxes if box.cls 0) print(f当前帧行人数量: {counts})conf 在这里从默认 0.25 提到 0.35原因是夜间场景误检率偏高路灯下的自行车、电线杆阴影都会让模型给出 0.2~0.35 的置信度输出。iou 从 0.5 提到 0.7是为了应对行人重叠时两个相邻框被 NMS 合并成一个的情况。这个一拉一抬的组合针对的是夜间监控里最典型的两种错误模式误检和漏检。如果要部署到边缘设备用 ONNX 导出比直接跑 PyTorch 权重更稳定yolo export modelruns/detect/night_person/weights/best.pt formatonnx opset12 imgsz640导出的 onnx 文件可以用 onnxruntime-gpu 在 Jetson 或工业计算机上推理M 芯片的 Mac 则可以直接用 CoreML 工具转换。博主提供的训练日志如果显示 mAP50 在 0.8 以上这个模型在遮挡不严重的夜间场景里可以直接进 demo如果 mAP50 在 0.6~0.7 区间部署时优先保证清晰主干道路的检测率把 conf 阈值再往上提 0.05配合区域划分规则而不是单帧结果做决策整体可用性会好很多。本文还有配套的精品资源点击获取

关于本文作者

来自尧图内容编辑团队

尧图内容编辑团队 内容团队

尧图内容编辑团队

本文由尧图网络内容编辑团队执笔。团队由资深项目经理、前端工程师与设计师组成,所有内容均来自亲手交付的真实项目,先讲清问题、再给出可落地的解法。尧图深耕北京网站建设十年,服务过京华建材集团、智造科技等各行业客户,把一线经验沉淀为可复用的行业观察。

  • 十年建站经验,覆盖建材、制造、服务、文创等
  • 项目经理把关选题与事实准确性
  • 工程师与设计师联合撰写专业细节
  • 统一编辑规范,保证文风与排版一致
  • 每月复盘转化数据,迭代选题方向

延伸阅读

相关资讯与近期热门内容

深度阅读推荐

建站决策前值得细读的三篇

网站改版的5个关键决策
2024-08-12

网站改版的5个关键决策

什么时候该改版、改到什么程度、如何避免流量掉光,京华建材集团改版复盘给出答案。

获取专属建站方案

看完文章,把您的行业与预算告诉我们,免费获取一份量身定制的官网建设方案与报价。

立即免费咨询