3. YOLOv8基础与模型架构

YOLOv8 是 Ultralytics 在 2023 年初推出的目标检测模型。说实话,它并不是一个颠覆性的创新,而是把之前 YOLOv5、YOLOX、YOLOv6 等版本里被验证有效的技巧,整合到了一个干净、高效的框架里。

我个人习惯把 YOLOv8 看作一个「模块化工具箱」。你不需要从零造轮子,只需要理解每个模块的作用,就能快速搭出适合自己业务的检测模型。这一章,我们就把它拆开来看。

3.1 整体网络结构:三件套

YOLOv8 延续了经典的 Backbone → Neck → Head 三段式设计。说白了,就是:

  • Backbone(骨干网络):负责提取图像特征。输入一张图,输出多个尺度的特征图。
  • Neck(颈部):负责融合特征。把 Backbone 输出的不同尺度特征图,通过上下采样和拼接,让信息流通起来。
  • Head(头部):负责预测。在融合后的特征图上,输出目标的类别、位置和置信度。

下面这张图是我自己画的 YOLOv8 结构简图,你可以对照着看:

YOLOv8 网络结构简图 Backbone(骨干网络) Conv + C2f Conv + C2f Conv + C2f SPPF Neck(颈部) FPN 上采样 PAN 下采样 特征拼接 Head(检测头) 解耦分类头 解耦回归头 DFL 分布损失 输出:类别 + 框 + 置信度
我的经验: 刚开始接触 YOLOv8 时,别急着看代码。先把这张图的结构记在脑子里,知道数据是怎么流的,后面看配置文件才不会晕。

3.2 Backbone 详解:C2f 与 SPPF

YOLOv8 的 Backbone 核心是两个模块:C2f 和 SPPF。

3.2.1 C2f 模块

C2f 是 YOLOv8 对之前版本 C3 模块的改进。C3 是「跨阶段局部网络」,C2f 则是「跨阶段局部网络 + 更多梯度流」。说白了,C2f 把输入的特征图分成两路,一路直接走捷径,另一路经过多个 Bottleneck 处理,最后再拼起来。

这样做的好处是:梯度可以更顺畅地回传到浅层网络,训练时不容易梯度消失。我在项目中遇到过,用 C2f 替换 C3 后,小目标的召回率提升了大概 2 个点。

3.2.2 SPPF 模块

SPPF(快速空间金字塔池化)是 YOLOv8 的标配。它用多个不同尺寸的池化核并行处理特征图,然后把结果拼在一起。这样模型就能同时看到「大范围」和「小范围」的上下文信息。

嗯,这里要注意:SPPF 比之前的 SPP 计算量更小,但效果几乎一样。如果你在部署时对速度有极致要求,可以考虑把 SPPF 的池化核尺寸调小一点。

3.3 Neck 详解:FPN + PAN 结构

Neck 部分,YOLOv8 沿用了 FPN(特征金字塔网络)+ PAN(路径聚合网络)的组合。FPN 负责把高层语义信息传递到低层,PAN 负责把低层位置信息传递到高层。两者结合,信息就双向流通了。

组件 作用 方向
FPN 将深层语义信息上采样,与浅层特征融合 自顶向下
PAN 将浅层位置信息下采样,与深层特征融合 自底向上

YOLOv8 在 Neck 里用了大量的拼接操作(Concat),而不是加法。拼接能保留更多原始信息,但也会增加通道数。所以后面通常会跟一个 1x1 卷积来降维。

避坑指南: 我曾经在 Neck 里自作聪明,把拼接改成了加法,想着能省点算力。结果小目标检测精度掉了 5 个点。后来才明白,拼接保留的原始位置信息对小目标太重要了。所以,除非你非常清楚自己在做什么,否则别轻易动 Neck 的结构。

3.4 Head 详解:解耦头与 DFL 损失

YOLOv8 的 Head 是它和 YOLOv5 最大的区别之一。它采用了 解耦头 和 DFL 损失。

3.4.1 解耦头

之前的 YOLO 版本,分类和回归任务共享同一个卷积层。YOLOv8 把它们分开了:一个分支负责分类,另一个分支负责回归。这样做的好处是,两个任务可以各自学习更专一的特征,互不干扰。

说白了,就是让分类的归分类,回归的归回归。我在实际部署中发现,解耦头对密集场景下的检测效果提升很明显。

3.4.2 DFL 损失

DFL(分布焦点损失)是 YOLOv8 在回归分支上用的新损失函数。传统的回归是直接预测一个坐标值,DFL 则是预测坐标值的概率分布。举个例子,传统方法直接预测 x=100,DFL 则预测 x 在 98、99、100、101、102 上的概率分布,然后取期望。

这样做的好处是:模型能知道自己的不确定性。如果分布很集中,说明模型很确定;如果分布很分散,说明模型在犹豫。这个信息在后处理时非常有用。

3.5 配置文件解读:yolov8n.yaml

YOLOv8 的配置文件是 YAML 格式的。我个人习惯,拿到一个新模型,第一件事就是看它的配置文件。下面以 yolov8n.yaml 为例,逐段解读。

# Ultralytics YOLOv8n
# 参数
nc: 80  # 类别数
scales:  # 模型缩放系数
  n: [0.33, 0.25, 1024]  # depth, width, max_channels

# Backbone
backbone:
  - [-1, 1, Conv, [64, 3, 2]]  # 0-P1/2
  - [-1, 1, Conv, [128, 3, 2]]  # 1-P2/4
  - [-1, 3, C2f, [128, True]]
  - [-1, 1, Conv, [256, 3, 2]]  # 3-P3/8
  - [-1, 6, C2f, [256, True]]
  - [-1, 1, Conv, [512, 3, 2]]  # 5-P4/16
  - [-1, 6, C2f, [512, True]]
  - [-1, 1, Conv, [1024, 3, 2]]  # 7-P5/32
  - [-1, 3, C2f, [1024, True]]
  - [-1, 1, SPPF, [1024, 5]]  # 9

# Head
head:
  - [-1, 1, nn.Upsample, [None, 2, "nearest"]]
  - [[-1, 6], 1, Concat, [1]]  # cat backbone P4
  - [-1, 3, C2f, [512]]  # 12

  - [-1, 1, nn.Upsample, [None, 2, "nearest"]]
  - [[-1, 4], 1, Concat, [1]]  # cat backbone P3
  - [-1, 3, C2f, [256]]  # 15 (P3/8-small)

  - [-1, 1, Conv, [256, 3, 2]]
  - [[-1, 12], 1, Concat, [1]]  # cat head P4
  - [-1, 3, C2f, [512]]  # 18 (P4/16-medium)

  - [-1, 1, Conv, [512, 3, 2]]
  - [[-1, 9], 1, Concat, [1]]  # cat head P5
  - [-1, 3, C2f, [1024]]  # 21 (P5/32-large)

  - [[15, 18, 21], 1, Detect, [nc]]  # Detect(P3, P4, P5)

解读几个关键点:

  • scales:定义了模型的深度、宽度和最大通道数。n 代表 nano,是最小的版本。你可以把 [0.33, 0.25, 1024] 理解为「把标准模型的层数乘以 0.33,通道数乘以 0.25,最大通道数限制在 1024」。
  • backbone 中的 [-1, 1, Conv, [64, 3, 2]]:-1 表示输入来自上一层,1 表示重复 1 次,Conv 是操作名,[64, 3, 2] 是参数:输出通道 64,卷积核 3x3,步长 2。
  • head 中的 [[-1, 6], 1, Concat, [1]]:[-1, 6] 表示把当前层的输出和第 6 层的输出拼接起来。这就是 FPN + PAN 的体现。
  • 最后的 Detect:[[15, 18, 21], 1, Detect, [nc]] 表示从第 15、18、21 层取特征图,分别对应小、中、大三个尺度的检测头。
我的建议: 如果你想修改模型结构,比如增加一个检测头来检测更小的目标,就在 head 的最后加上一层特征图,然后在 Detect 里把它的索引加进去。但要注意,增加检测头会带来额外的计算量。

3.6 不同版本对比:n/s/m/l/x

YOLOv8 提供了 5 个预训练版本,从 nano 到 xlarge。它们的区别主要体现在深度和宽度上。

版本 深度系数 宽度系数 参数量 (M) FLOPs (G) mAP50-95
n (nano) 0.33 0.25 3.2 8.7 37.3
s (small) 0.33 0.50 11.2 28.6 44.9
m (medium) 0.67 0.75 25.9 78.9 50.2
l (large) 1.00 1.00 43.7 165.2 52.9
x (xlarge) 1.00 1.25 68.2 257.8 53.9

从表格可以看出,nano 版本参数量只有 3.2M,非常适合边缘设备部署。而 xlarge 版本虽然精度最高,但计算量也最大。我在工业项目里,通常先用 nano 或 small 版本做快速验证,确认方案可行后,再根据硬件资源选择 larger 版本。

选型建议: 如果你的设备是 Jetson Nano 或树莓派,用 n 或 s 版本。如果是 Jetson Orin 或高端 GPU,可以考虑 m 或 l 版本。x 版本除非你对精度有极致要求,否则不推荐,性价比不高。

好了,这一章的内容就到这里。YOLOv8 的结构其实不复杂,关键是把 Backbone、Neck、Head 这三个部分理解透,再学会看配置文件,后面做模型修改和部署就会顺手很多。