1. 认识BDD100K数据集与YOLOv5s

第一次接触自动驾驶目标检测时,我被各种数据集和算法搞得晕头转向。直到遇到BDD100K这个"全能选手",才发现它简直是新手练级的完美选择。这个由伯克利大学发布的数据集包含10万段驾驶视频,覆盖了城市街道、高速公路、隧道等多样化场景,甚至连雨雪天气和夜间行驶的情况都考虑到了。最让我惊喜的是,它标注了13类常见交通对象——从行人、车辆到不同颜色的交通灯,完全就是现实道路的微缩版。

YOLOv5s作为目标检测界的"轻量级拳王",特别适合我们这些刚入门的开发者。相比前代版本,它的训练速度更快,模型体积更小,但精度却毫不逊色。我实测下来,用普通游戏本(RTX 3060显卡)训练模型,一天就能跑完基础实验。这里要特别说明下,YOLOv5系列其实有多个版本:

  • YOLOv5s:最小最快的版本(适合快速验证)
  • YOLOv5m:平衡型选手
  • YOLOv5l:精度优先
  • YOLOv5x:巨无霸模型

对于初次尝试,我强烈建议从YOLOv5s开始。它的模型文件只有14MB左右,但检测速度能达到140FPS,完全能满足实时性要求。记得第一次看到自己的模型在视频里框出车辆和行人时,那种成就感简直爆棚!

2. 数据预处理实战技巧

原始数据就像刚挖出来的矿石,需要精心打磨才能用。BDD100K的标注文件是JSON格式,而YOLOv5需要特定的TXT格式,这个转换过程我踩过不少坑。这里分享一个完整解决方案:

首先需要安装转换工具包:

pip install pycocotools labelme2coco

关键步骤1:JSON转COCO格式 我修改了官方提供的转换脚本,特别处理了交通灯颜色分类问题。核心逻辑是遍历每个标注对象,提取box坐标和类别信息。遇到交通灯时,会额外读取颜色属性:

for label in img_data['labels']:
    if label['category'] == 'traffic light':
        color = label['attributes']['trafficLightColor']
        new_category = f"tl_{color}"
        # 后续处理逻辑...

关键步骤2:COCO转YOLO格式 这里要注意坐标系的转换。COCO用的是左上角坐标+宽高,而YOLO需要中心点坐标+归一化值。我写了个转换函数:

def coco2yolo(bbox, img_w, img_h):
    x_center = (bbox[0] + bbox[2]/2) / img_w
    y_center = (bbox[1] + bbox[3]/2) / img_h
    width = bbox[2] / img_w
    height = bbox[3] / img_h
    return [x_center, y_center, width, height]

注意:一定要检查转换后的标签文件是否与图像对齐。我常用OpenCV画框验证:

cv2.rectangle(img, (x1,y1), (x2,y2), (0,255,0), 2)

3. 环境配置避坑指南

配环境就像搭积木,少一块都不行。经过多次实践,我总结出最稳定的配置方案:

基础环境:

  • Python 3.8(3.7+都可以)
  • PyTorch 1.10 + CUDA 11.3
  • Ubuntu 20.04(Windows也可但建议WSL2)

这是我的requirements.txt精华版:

torch==1.10.0+cu113
torchvision==0.11.1+cu113
opencv-python>=4.5.4
matplotlib>=3.3.0
pycocotools>=2.0
tqdm>=4.64.0

安装时有个小技巧:先装PyTorch再装其他依赖,能避免版本冲突:

pip install torch torchvision --extra-index-url https://download.pytorch.org/whl/cu113
pip install -r requirements.txt

数据集配置文件: 在data目录下新建bdd100k.yaml,内容要特别注意路径设置:

train: ../bdd100k/images/train
val: ../bdd100k/images/val
nc: 13
names: ['person','rider','car',...,'tl_none']

遇到过最头疼的问题是路径错误,建议:

  1. 使用绝对路径更稳妥
  2. 在Python中打印当前路径确认:
import os
print(os.path.abspath('.'))

4. 模型定制与调优策略

直接套用默认模型就像穿别人的衣服,总有不合适的地方。我们需要量体裁衣:

模型结构调整: 修改models/yolov5s.yaml,重点调整两个参数:

nc: 13  # 类别数
anchors:  # 建议使用autoanchor自动计算
  - [10,13, 16,30, 33,23] 
  - [30,61, 62,45, 59,119]
  - [116,90, 156,198, 373,326]

超参数优化: 在data/hyps/hyp.scratch-low.yaml中,我调整了这些关键参数:

lr0: 0.01     # 初始学习率
lrf: 0.1      # 最终学习率
momentum: 0.937
weight_decay: 0.0005
fl_gamma: 0.5  # 焦点损失gamma

训练技巧:

  1. 预热训练:前3个epoch用小学习率
  2. 自动锚框:--autoanchor参数
  3. 混合精度:--half参数节省显存

完整训练命令示例:

python train.py --img 640 --batch 32 --epochs 100 \
--data bdd100k.yaml --cfg yolov5s.yaml \
--weights yolov5s.pt --cache --device 0

5. 训练过程监控与分析

训练不是设好参数就完事,要像教练盯着运动员一样关注模型表现。

关键指标解读:

  • mAP@0.5:IoU阈值0.5时的平均精度
  • mAP@0.5:0.95:综合精度指标
  • Precision/Recall:精确率与召回率

我用TensorBoard监控训练过程:

tensorboard --logdir runs/train

常见问题解决方案:

现象 可能原因 解决方法
损失不下降 学习率太高 减小lr0
mAP波动大 batch size太小 增大batch
过拟合 数据量不足 数据增强

我的调参记录:

  1. 初始阶段:发现val_loss震荡,将lr0从0.01降到0.005
  2. 中期阶段:增加--cos-lr参数使用余弦退火
  3. 后期阶段:启用--label-smoothing 0.1防止过拟合

6. 模型评估与部署实战

训练完成不是终点,如何用好模型才是关键。

评估命令:

python val.py --weights runs/train/exp/weights/best.pt \
--data bdd100k.yaml --img 640 --task test

部署方案对比:

方案 优点 缺点
PyTorch原生 简单直接 依赖环境
ONNX Runtime 跨平台 需要转换
TensorRT 极致性能 配置复杂

我常用的ONNX转换命令:

python export.py --weights best.pt --include onnx \
--img 640 --simplify --dynamic

实际应用示例:

import torch
model = torch.hub.load('ultralytics/yolov5', 'custom', 'best.pt')
results = model('test.jpg')
results.show()  # 显示检测结果

7. 性能优化进阶技巧

当基础模型跑通后,我开始追求更极致的性能。

数据增强策略: 在data/hyps/hyp.scratch-low.yaml中添加:

hsv_h: 0.015  # 色相增强
hsv_s: 0.7    # 饱和度增强
hsv_v: 0.4    # 明度增强
flipud: 0.5   # 上下翻转概率

模型剪枝: 使用TorchPruner进行通道剪枝:

from torchpruner import SparsePruner
pruner = SparsePruner(model, sparsity=0.3)
pruner.step()

量化部署: 将模型转为INT8提升推理速度:

python export.py --weights best.pt --include engine \
--img 640 --device 0 --half

经过这些优化,我的模型在Jetson Xavier上达到了58FPS,完全满足实时性要求。记得第一次看到优化后的模型在车载设备上流畅运行时,真切感受到了AI技术的魅力。

Logo

汇聚全球AI编程工具,助力开发者即刻编程。

更多推荐