当前位置: 首页 > news >正文

零基础入门AI: YOLOv5 详解与项目实战

一、YOLOv5 概述

1.1 基本介绍

YOLOv5(You Only Look Once version 5)是一个开源的目标检测框架,由 Glenn Jocher 及其团队开发,属于 Ultralytics 公司,在 GitHub 上发布。它是 YOLO 系列算法的第五代版本,旨在提供高效、灵活且易于使用的物体检测解决方案。相比于之前的版本,YOLOv5 引入了许多改进,使其成为工业界和学术界广泛采用的选择。

1.2 版本规格

YOLOv5 有 YOLOv5n、YOLOv5s、YOLOv5m、YOLOv5l、YOLOv5x 五个版本。这几个模型的结构基本一样,不同的是depth_multiple 模型深度和 width_multiple 模型宽度这两个参数。就和我们买衣服的尺码大小排序一样,YOLOv5n 网络是 YOLOv5系列中深度最小、特征图的宽度最小的网络。其他三种都是在此基础上不断加深,不断加宽其参数量依次上升,当然了其效果也是越来越好。

性能对比表:

模型尺寸(像素)mAPval 50-95mAPval 50参数量(M)FLOPs@640(B)适用场景
YOLOv5n64028.045.71.94.5移动设备/嵌入式系统
YOLOv5s64037.456.87.216.5边缘设备
YOLOv5m64045.464.121.249.0常规硬件
YOLOv5l64049.067.346.5109.1高端硬件
YOLOv5x64050.768.986.7205.7高性能硬件

1.3 主要特点

  • 高性能

    • YOLOv5 在多种硬件平台上表现出色,特别适合实时目标检测任务
    • 通过优化网络结构和训练流程,YOLOv5 在多种数据集上达到了较高的精度和较快的推理速度
  • 易于使用

    • YOLOv5 提供了简洁的 API 和详细的文档,使得用户可以轻松地进行模型训练、评估和部署
    • 支持多种框架和语言,包括 PyTorch、ONNX、TensorRT 等
  • 模块化设计

    • YOLOv5 采用了模块化的设计理念,使得用户可以方便地进行模型定制和扩展
    • 支持多种预训练模型和配置文件,用户可以根据自己的需求选择合适的模型

二、技术架构与核心改进

2.1 主要改进点

  • 主干网络是修改后的 CSPDarknet53,后面跟了 SPPF 模块
  • 网络最开始增加 Focus 结构
  • 颈部网络采用 PANet、FPN
  • 激活函数换成了 SiLU、Swish
  • 采用 CloU 损失

2.2 Focus 模块(早期版本)

YOLOv5 刚推出时,为了提升模型效率,采用了 Focus 模块 作为网络的初始特征提取层,传统卷积下采样会丢失部分空间信息,Focus 模块旨在在不丢失信息的前提下进行高效下采样

核心目标: 将高分辨率图像的空间信息通过切片操作转换为通道信息,从而实现高效、无信息损失的下采样。

Focus 模块是一种用于特征提取的卷积神经网络层,用于将输入特征图中的信息进行压缩和组合,从而提取出更高层次的特征表示,它被用作网络中的第一个卷积层,用于对输入特征图进行下采样,以减少计算量和参数量。

Focus 层在 YOLOv5 中是图片进入主干网络前,对图片进行切片操作,原理与 Yolov2 的 passthrough 层类似,采用切片操作把高分辨率的图片(特征图)拆分成多个低分辨率的图片(特征图),即隔列采样+拼接。

具体操作流程:

  1. 输入阶段:假设输入一张图像大小为 640x640x3
  2. 切片操作:640 x 640 x 3的图像输入 Focus 结构,采用切片操作,每隔一个像素拿到一个值
  3. 拼接转换:然后进行一个连接(concat),变成 320 x 320 x 12 的特征图
  4. 卷积处理:经过一次 32 个卷积核的卷积操作,最终输出 320 x 320 x 32 的特征图

注意: 在 YOLOv5 刚提出来的时候,有 Focus 结构,从 YOLOv5 第六版开始,就舍弃了这个结构,改用 k=6×6,stride=2 的常规卷积。

2.3 网络结构

在这里插入图片描述

YOLOv5 的整体网络结构基于 CSPDarknet53 主干网络和 PANet 颈部网络,包含以下几个核心组件:

2.3.1 CSP1_X 与 CSP2_X
  • CSP1_X

    • 定义:带 shortcut(残差连接)的 CSP 模块
    • 结构特点:内部包含带有 shortcut 的 Bottleneck 结构
    • 应用场景:主要用于 backbone 部分,如 CSPDarknet53,增强特征提取能力
    • X 的含义:表示 bottleneck 的数量
  • CSP2_X

    • 定义:不带 shortcut 的 CSP 模块
    • 结构特点:内部没有 shortcut 连接,仅通过卷积操作进行特征提取
    • 应用场景:主要用于 neck 部分,如 PANet(Path Aggregation Network),进行特征聚合
    • X 的含义:表示 bottleneck 或其他卷积模块的数量
2.3.2 自适应Anchor的计算

在 YOLOv3、YOLOv4 中,训练不同的数据集时,计算初始 Anchor 的值是通过单独的程序运行的。但 YOLOv5 中将此功能嵌入到代码中,每次训练时会自适应的计算不同训练集中的最佳 Anchor 值。

实现方式:

  • 在训练开始前,YOLOv5 会自动加载训练集中的标注框
  • 使用 K-Means 聚类算法计算 Anchor
  • 将结果作为初始 Anchor 值用于模型初始化

源码位置: utils/autoanchor.py/check_anchors()

2.3.3 激活函数

YOLOv5 使用了 SiLU 激活函数、Swish 激活函数两种激活函数。

SiLU 激活函数:

  • YOLOv5 的 Backbone 和 Neck 模块和 YOLOv4 中大致一样,都采用 CSPDarkNet 和 FPN+PAN 的结构,但是网络中其他部分进行了调整,其中 YOLOv5 使用的激活函数是 SiLU
  • 数学表达式:SiLU(x)=x⋅σ(x)SiLU(x) = x·\sigma(x)SiLU(x)=xσ(x)
  • 特性:具备无上界有下届、平滑、非单调的特性

Swish 激活函数:

  • Swish 激活函数是一个近似于 SiLU 函数的非线性激活函数
  • 数学表达式:Swish(x)=x⋅σ(βx)Swish(x) = x·\sigma(\beta x)Swish(x)=xσ(βx)
  • β\betaβ是一个可调节的参数,通常设定为 1
2.3.4 Bottleneck 结构

Bottleneck 是用于减少参数和计算量的结构,其设计灵感来自于ResNet。

结构组成:

  • 1x1卷积:用于减少特征图的通道数
  • 3x3卷积:用于提取特征,后接一个 Batch Normalization 层和 ReLU 激活函数
  • 1x1卷积:用于恢复特征图的通道数,后接一个BN层
  • 跳跃连接(Shortcut):将输入直接加到输出上,以形成残差连接
2.3.5 C3 模块

YOLOv5 中的 C3 模块在 CSP上进行了优化,非常相似但略有不同。YOLOv5 一共使用过两种 CSP 模块:

BottleneckCSP(v4.0版本之前):

  • 结构特点: 包含多个带 shortcut 的 Bottleneck
  • 激活函数:LeakyReLU
  • 用途:主要用于早期 YOLOv5 的 backbone

在这里插入图片描述

C3(v4.0版本之后):

  • 结构特点: 不再使用 shortcut(即 Bottleneck 不带残差连接)
  • 激活函数:SiLU
  • 用途:广泛用于 backbone 和 neck(如 PANet)

在这里插入图片描述

2.3.6 SPPF 模块

SPPF(Spatial Pyramid Pooling Fast)模块是对SPP模块的优化改进。

创新点:

  • 将卷积核大小变成相同,然后将并行变成了串行+并行
  • 2个K5池化=1个K9池化,3个K5池化=1个K13池化
  • 在结果相同的基础上,速度更快,计算量更小

在这里插入图片描述

等效感受野计算公式:
对于连续堆叠 n 层,每层使用大小为 k 的核的操作(例如卷积或池化),其等效感受野大小可以通过以下公式计算:
K等效=1+n(k−1)K_{等效}=1+n(k−1)K等效=1+n(k1)

层数 n卷积核大小 k等效感受野
151+1×(5−1)=5
251+2×(5−1)=9
351+3×(5−1)=13

SPP 和 SPPF 区别:
SPPF通过串行连接多个池化层来实现与SPP相同的多尺度特征提取效果,但计算效率更高。

在这里插入图片描述

2.4 输出头设计

YOLOv5 的输出头设计灵活度较高,支持多种尺寸:

  • 输入图像尺寸:通常为 640x640(或者其它尺寸,如 416x416 等)
  • 输出特征图:YOLOv5 使用大、中、小三个尺寸
  • 输出尺寸:
    • 大目标: 通常是输入图像尺寸的 1/32
    • 中目标: 通常是输入图像尺寸的 1/16
    • 小目标: 通常是输入图像尺寸的 1/8

计算公式:
假设输入图像尺寸为640x640,具体的特征图尺寸如下:
大目标:64032×64032=20×20中目标:64016×64016=40×40小目标:6408×6408=80×80 \text{大目标:}\frac{640}{32}\times\frac{640}{32}=20\times20\\ \text{中目标:}\frac{640}{16}\times\frac{640}{16}=40\times40\\ \text{小目标:}\frac{640}8\times\frac{640}8=80\times80 大目标:32640×32640=20×20中目标:16640×16640=40×40小目标:8640×8640=80×80

三、实战应用

3.1 开源项目介绍

YOLOV5并没有学术论文,是一个开源项目,是 Ultralytics 公司于 2020 年6月9 日发布的。项目可以在 GitHub 上获取:【https://github.com/ultralytics/yolov5】

预训练模型说明:
这些模型的结构是一样的,区别在于网络的深度和宽度,网络的深度指的就是 C3 模块中 Bottleneck 的数量,网络的宽度是指网络每层输出的通道数。

3.2 项目构建与配置

3.2.1 项目获取
  1. 通过 GitHub 获取官方源码:【https://github.com/ultralytics/yolov5】
  2. 国内用户可以使用 Gitee 镜像:【https://gitee.com/monkeycc/yolov5】
  3. 将源码复制到项目开发文件夹中
3.2.2 环境配置
  1. 配置 Python 解释器(建议使用 Anaconda 创建的虚拟环境)
  2. 安装 requirements.txt 中的依赖(已安装PyTorch的情况下注释掉相关行)
pip install -r requirements.txt -i https://pypi.tuna.tsinghua.edu.cn/simple
3.2.3 模型下载

从官方提供的模型库中下载合适的预训练模型,复制到项目中。

3.3 快速入门

3.3.1 推理测试

使用以下命令进行推理测试:

python detect.py --weights yolov5s.pt --source data/images/bus.jpg

参数说明:

  • --weights: 指定模型权重文件路径
  • --source: 指定输入源,可以是图像、视频、摄像头、目录等
  • 推理结果默认保存到 runs/detect 目录
3.3.2 数据集获取与标注

数据集来源:

  • 安全帽数据集:【https://www.kaggle.com/datasets/snehilsanyal/construction-site-safety-image-dataset-roboflow】

标注工具:

  • 使用 labelImg 工具进行标注
  • 安装:pip install labelimg
  • 启动:在激活环境下执行 labelimg 命令

在这里插入图片描述

标注流程:

  1. 选择 YOLO 模式创建标签
  2. 使用快捷键进行标注:
    • w: 绘制矩形框
    • d: 下一张图片
    • a: 上一张图片
    • Del: 删除标注框
    • Ctrl+s: 保存

标注结果:

  • 生成 .txt 文件:存储每一张图片的标注信息(标签序号、标注框的中心坐标、标注框的相对宽和高)
  • 生成 classes.txt:类别信息文件
3.3.3 数据集配置
  1. 在项目中创建 datasets 文件夹
  2. datasets 中创建子文件夹(如 helmet)存放数据集
  3. 复制并修改配置文件:
    • 复制 data/coco128.yamlhelmet.yaml
    • 修改路径和类别信息

配置文件示例:

path: ./datasets/helmet
train: train/images
val: val/images
test: names:0: head1: helmet2: person
  1. 修改模型配置文件 models/yolov5s.yaml 中的类别数

3.4 模型训练

3.4.1 训练命令
python train.py \--data data/helmet.yaml \--img 640 \--epochs 25 \--weights yolov5s.pt \--cfg models/yolov5s.yaml \--batch-size 2 \--device 0

参数说明:

  • --data: 数据集配置文件路径
  • --img: 输入图像尺寸
  • --epochs: 训练周期数
  • --weights: 初始权重文件路径
  • --cfg: 模型配置文件路径
  • --batch-size: 批量大小
  • --device: 训练设备(0表示GPU 0,cpu表示CPU)
3.4.2 训练过程监控

训练过程中显示的关键指标:

  • Epoch: 训练进度
  • Gpu_mem: GPU内存使用情况
  • box_loss: 边界框回归损失
  • obj_loss: 对象存在性损失
  • cls_loss: 分类损失
  • Instances: 检测到的目标实例数量
  • Size: 输入图像大小
3.4.3 恢复训练

如果训练过程中意外停止,可以使用以下命令恢复训练:

python train.py --weights runs/train/exp/weights/last.pt --resume

3.5 模型导出与推理

3.5.1 导出ONNX格式
python export.py --weights yolov5s.pt --img 640 --batch 1 --device 0 --include onnx
3.5.2 YOLO格式推理
from yolov5 import detect
detect.run(weights='yolov5s.onnx',  # 权重文件路径source='data/images',  # 输入源路径img_size=640,  # 输入图像尺寸conf_thres=0.25,  # 置信度阈值iou_thres=0.45,  # IoU阈值max_det=1000,  # 最大检测数量device='0',  # 设备view_img=False,  # 显示检测结果save_txt=False,  # 保存检测结果为txt文件save_conf=False,  # 保存置信度到txt文件save_crop=False,  # 裁剪并保存检测到的对象nosave=False,  # 保存图像/视频classes=None,  # 检测所有类agnostic_nms=False,  # 类无关的非极大值抑制augment=False,  # 推理增强visualize=False,  # 可视化特征图update=False,  # 更新所有模型project='runs/detect',  # 结果保存目录name='exp',  # 结果保存子目录exist_ok=False,  # 允许现有目录line_thickness=3,  # 画框线条粗细hide_labels=False,  # 隐藏标签hide_conf=False,  # 隐藏置信度half=False,  # 半精度推理dnn=False  # 使用OpenCV DNN模块
)
3.5.3 ONNX格式推理
import onnxruntime as ort
import numpy as np
import cv2# 创建ONNX Runtime推理会话
providers = ['CUDAExecutionProvider']  # 或 ['CPUExecutionProvider']
session = ort.InferenceSession('yolov5s.onnx', providers=providers)# 预处理图像
img = cv2.imread('data/images/bus.jpg')
img = cv2.resize(img, (640, 640))
img = img.transpose((2, 0, 1))  # HWC to CHW
img = np.expand_dims(img, axis=0).astype(np.float32) / 255.0# 推理
outputs = session.run(None, {'images': img})
print(outputs[0].shape)

四、项目结构与配置详解

4.1 源码目录结构

yolov5/
├── data/                 # 数据集配置和超参数
│   ├── hyps/            # 超参数配置
│   ├── images/          # 测试图像
│   ├── scripts/         # 数据集下载脚本
│   └── *.yaml          # 数据集配置文件
├── models/              # 模型定义
│   ├── common.py        # 通用模块
│   ├── experimental.py  # 实验性代码
│   ├── tf.py           # TensorFlow版本
│   ├── yolo.py         # YOLO特定模块
│   └── *.yaml          # 模型配置文件
├── utils/               # 工具函数
│   ├── activations.py   # 激活函数
│   ├── augmentations.py # 数据增强
│   ├── autoanchor.py    # 自动Anchor计算
│   ├── dataloader.py    # 数据加载
│   ├── loss.py          # 损失函数
│   └── metrics.py       # 评估指标
├── datasets/            # 自定义数据集
├── runs/                # 训练和推理结果
├── detect.py            # 目标检测脚本
├── train.py             # 训练脚本
├── val.py               # 验证脚本
└── requirements.txt     # 依赖环境

4.2 数据集目录结构

datasets/
└── helmet/              # 数据集名称├── test/            # 测试集(可选)│   └── images/      # 测试图像├── train/           # 训练集│   ├── images/      # 训练图像│   └── labels/      # 标注文件└── valid/           # 验证集├── images/      # 验证图像└── labels/      # 标注文件

4.3 训练结果目录

runs/
├── detect/              # 推理结果
│   └── exp/             # 实验1,依次递增
└── train/               # 训练结果└── exp/             # 实验1,依次递增└── weights/     # 模型权重├── best.pt  # 最佳权重└── last.pt  # 最后权重

4.4 训练参数配置详解

超参数文件: data/hyps/ 目录下的yaml文件

主要参数说明:

  • lr0: 初始学习率 (SGD=1E-2, Adam=1E-3)
  • lrf: 最终学习率 (lr0 * lrf)
  • momentum: SGD动量/Adam beta1
  • weight_decay: 优化器权重衰减
  • warmup_epochs: 热身周期数
  • box: 边界框损失增益
  • cls: 分类损失增益
  • obj: 目标检测损失增益
  • hsv_h: 图像HSV-Hue增强
  • hsv_s: 图像HSV-Saturation增强
  • hsv_v: 图像HSV-Value增强
  • flipud: 图像上下翻转概率
  • fliplr: 图像左右翻转概率
  • mosaic: 图像马赛克增强概率

4.5 模型结构参数详解

模型配置文件: models/ 目录下的yaml文件

主要参数:

  • nc: 类别数量
  • depth_multiple: 模型深度系数
  • width_multiple: 层通道数系数
  • anchors: 锚框配置
  • backbone: 主干网络结构
  • head: 检测头结构

模块定义格式: [from, number, module, args]

  • from: 输入来源(-1表示上一层)
  • number: 模块重复次数
  • module: 模块名称(定义在common.py中)
  • args: 初始化参数

五、扩展功能应用

5.1 实例分割

下载yolov5s-seg.pt文件、自己训练,可以看开发手册:【https://docs.ultralytics.com/tasks/classify/】

python segment/predict.py --weights yolov5s-seg.pt --source data/images/bus.jpg

5.2 图像分类

下载yolov5s-cls.pt文件、自己训练,可以看开发手册:【https://docs.ultralytics.com/tasks/classify/】

python classify/predict.py --weights yolov5s-cls.pt --source data/images/bus.jpg

六、项目实战:车牌检测与识别

6.1 项目介绍

使用 YOLOv5 框架完成目标检测任务,实现车牌检测和号码识别。

技术流程:

  1. 目标检测阶段:找到车牌位置并裁剪保存
  2. 文字识别阶段:使用 PaddleOCR 识别车牌号码

6.2 数据集处理

6.2.1 数据集获取
  • 使用 CCPD(中国城市车牌数据集)
  • 开源地址:【https://gitcode.com/Resource-Bundle-Collection/f81da/】
6.2.2 标注数据处理
  • 从文件名解析标注信息(包含坐标信息)
  • 坐标转换:左上/右下坐标 → 中心点+宽高(归一化)
  • 单类别标注:车牌(类别0)
  • 按标准格式组织训练集和验证集

6.3 模型训练

  • 使用 yolov5s.pt 作为预训练权重
  • 初始训练200个epochs,根据效果调整
  • 监控训练指标,适时调整超参数

6.4 推理与集成

import torch
from PIL import Image# 加载自定义模型
model = torch.hub.load('ultralytics/yolov5', 'custom', path='license_plate.pt')# 推理
results = model('input_image.jpg')# 裁剪检测区域
crops = results.crop()
for crop in crops:plate_image = crop['im']  # 提取车牌图像# 接入PaddleOCR进行文字识别

七、实践与优化

7.1 性能优化

  1. 数据增强策略:根据模型尺寸选择合适的增强强度
  2. 超参数调优:参考官方提供的超参数配置文件
  3. 模型量化:导出ONNX/TensorRT格式提升推理速度
  4. 硬件加速:合理配置batch size以避免内存溢出

7.2 训练技巧

  1. 学习率调度:使用cosine annealing或one-cycle策略
  2. 早停机制:监控验证集性能,防止过拟合
  3. 模型集成:融合多个模型的预测结果提升精度
  4. 数据平衡:处理类别不平衡问题,使用focal loss等

7.3 部署考虑

  1. 模型格式选择:根据部署环境选择pt、onnx或tensorrt格式
  2. 内存优化:使用半精度(float16)推理减少内存占用
  3. 批量处理:合理设置batch size平衡延迟和吞吐量
  4. 硬件适配:针对不同硬件平台进行特定优化

八、资源与支持

8.1 官方资源

  • GitHub仓库:【https://github.com/ultralytics/yolov5】
  • 官方文档:【https://docs.ultralytics.com/】
  • 预训练模型:【https://github.com/ultralytics/yolov5/tree/master/models】

8.2 社区支持

  • GitHub Issues:问题反馈和功能请求
  • Discord社区:实时交流和技术讨论
  • Stack Overflow:技术问题解答

8.3 学习资源

  • 官方教程:包含从入门到进阶的完整指南
  • 论文解读:相关技术论文和分析文章
  • 实战案例:各种应用场景的实现示例

注意: 本文档基于 YOLOv5 v7.0 版本编写,不同版本可能存在差异,请以官方文档和代码为准。建议定期查看官方更新以获取最新特性和优化。

http://www.xdnf.cn/news/1465111.html

相关文章:

  • 数据库存储大量的json文件怎么样高效的读取和分页,利用文件缓存办法不占用内存
  • 数据结构:排序
  • 【Day21】146.LRU缓存 (Least Recently Used)
  • 详细解读Docker
  • STC携手VEX发起全球首个碳资产RWA生态,泰国峰会即将引爆绿色金融
  • 飞算JavaAI炫技赛:电商系统开发全流程实战解析
  • 卫星在轨光压计算详解
  • openharmony之AV_CodeC音视频编解码模块详解(二)
  • (未完待续...)如何编写一个用于构建python web项目镜像的dockerfile文件
  • Kubernetes实战系列(4)
  • v4l2设置图像分辨率失败的问题
  • react+umi项目如何添加electron的功能
  • PyTorch 中.backward() 详解使用
  • 前后端国密加密传输用户密码流程
  • Unity 解决天空盒中间出现一条线
  • flink 伪代码
  • 高效管理网络段和端口集合的工具之ipset
  • Bug排查日记:高效记录与解决之道
  • 高通AR1平台Recovery架构分析与自动恢复出厂设置实现
  • 从 elecworks 到云端协同:SOLIDWORKS Electrical 发展历史 + 核心功能 + 采购指南
  • Linux 磁盘扩容及分区相关操作实践
  • 从Java全栈到云原生:一场技术深度对话
  • Golang语言设计理念
  • 【GEOS-Chem伴随模型第一期】GEOS-Chem Adjoint 模型详解
  • 常见Bash脚本漏洞分析与防御
  • 【Flutter】RefreshIndicator 无法下拉刷新问题
  • 【存储选型终极指南】RustFS vs MinIO:5大维度深度对决,95%技术团队的选择秘密!
  • LeetCode 131 分割回文串
  • 【LeetCode热题100道笔记】删除链表的倒数第 N 个结点
  • Kafka核心原理与常见面试问题解析