我们来逐项、逐符号、用通俗语言+例子,彻底讲清楚 YOLOv1 的损失函数(Loss Function)到底在算什么、为什么这样设计。


🎯 损失函数的目标是什么?

YOLOv1 要同时完成三件事:

  1. 定位物体(预测边界框的 x, y, w, h)
  2. 判断有没有物体(置信度 confidence)
  3. 识别物体类别(如“狗”、“车”)

所以它的损失函数必须同时监督这三部分,而且要聪明地分配权重——不能让某一部分“压垮”其他部分。


📐 整体结构:5 个部分相加

YOLOv1 的总损失 $ \mathcal{L} $ 是以下 5 项之和

监督内容 只对哪些网格/框计算?
1️⃣ 坐标损失(x, y) 框中心位置 有物体的网格中,负责预测的那个框
2️⃣ 尺寸损失(w, h) 框宽高 同上
3️⃣ 有物体的置信度损失 confidence 应接近 IoU 同上
4️⃣ 无物体的置信度损失 confidence 应接近 0 所有不含物体中心的网格的所有框
5️⃣ 分类损失 类别概率 有物体的网格(整个网格,不是每个框)

✅ 注意:只有真实物体中心所在的那个网格才算“有物体”。


🔍 逐项详解(配合符号说明)

符号说明(先搞懂这些!)

  • $ S = 7 $:图像被分成 7×7 网格
  • $ B = 2 $:每个网格预测 2 个边界框
  • $ i $:网格索引(从 0 到 $S^2 - 1$,共 49 个)
  • $ j $:框索引(0 或 1)
  • $ \mathbb{1}_{ij}^{\text{obj}} $:指示函数
    • 如果第 $i$ 个网格中的第 $j$ 个框“负责”预测某个真实物体 → 值为 1
    • 否则为 0
  • $ \mathbb{1}_{i}^{\text{obj}} $:如果第 $i$ 个网格包含某个物体的中心 → 为 1(用于分类损失)
  • $ x_i, y_i $:模型预测的框中心(相对于网格左上角,归一化到 [0,1])
  • $ \hat{x}_i, \hat{y}_i $:真实值(ground truth)
  • $ w_i, h_i $:预测的宽高(相对于整图,可 >1)
  • $ \hat{w}_i, \hat{h}_i $:真实宽高
  • $ C_i $:预测的置信度(confidence)
  • $ \hat{C}_i $:目标置信度(训练时 = 预测框与真实框的 IoU)
  • $ p_i© $:预测的“该网格物体属于类别 c”的概率
  • $ \hat{p}_i© $:真实标签(one-hot 编码,如“狗”=1,其余=0)

第1项:框中心坐标损失(x, y)

$$
\lambda_{\text{coord}} \sum_{i=0}^{S^2} \sum_{j=0}^{B} \mathbb{1}_{ij}^{\text{obj}} \left[ (x_i - \hat{x}_i)^2 + (y_i - \hat{y}_i)^2 \right]
$$

含义
只对“负责预测真实物体”的那些框,计算其中心点预测误差。

📌 关键点

  • 只有一个框会被选中(IoU 更大的那个),所以 $\mathbb{1}_{ij}^{\text{obj}}$ 大部分是 0。
  • L2 损失(平方误差),惩罚大偏差。
  • 乘以 $\lambda_{\text{coord}} = 5$:强调定位很重要!

💡 举例:
真实物体中心在网格 (3,4),两个预测框 A 和 B。
A 与真实框 IoU=0.6,B=0.3 → 选 A。
只计算 A 的 (x,y) 误差,B 的不算。


第2项:框尺寸损失(w, h)——但用了 √!

$$
\lambda_{\text{coord}} \sum_{i=0}^{S^2} \sum_{j=0}^{B} \mathbb{1}_{ij}^{\text{obj}} \left[ (\sqrt{w_i} - \sqrt{\hat{w}_i})^2 + (\sqrt{h_i} - \sqrt{\hat{h}_i})^2 \right]
$$

含义:同样只对“负责框”计算宽高误差,但对 w 和 h 开平方后再算误差

为什么要开平方?

👉 解决小物体误差被大物体淹没的问题。

  • 假设真实宽 = 0.1(小物体),预测 = 0.2 → 误差 = 0.01(平方后)
  • 真实宽 = 0.9(大物体),预测 = 1.0 → 误差 = 0.01(一样!)
  • 但实际上,小物体预测错一倍,比大物体错一点点更严重!

开平方后

  • 小物体:√0.1 ≈ 0.316,√0.2 ≈ 0.447 → 差 ≈ 0.131 → 平方 ≈ 0.017
  • 大物体:√0.9 ≈ 0.949,√1.0 = 1.0 → 差 ≈ 0.051 → 平方 ≈ 0.0026

小物体的损失变大了!模型会更关注它。


第3项:有物体的置信度损失

$$
\sum_{i=0}^{S^2} \sum_{j=0}^{B} \mathbb{1}_{ij}^{\text{obj}} (C_i - \hat{C}_i)^2
$$

含义:让“负责框”的置信度 $C_i$ 接近 它与真实框的 IoU

  • 如果预测框和真实框完全重合 → IoU=1 → 希望 $C_i = 1$
  • 如果重合度低 → IoU=0.5 → 希望 $C_i = 0.5$

📌 注意:这不是让 confidence=1,而是让它等于 定位质量(IoU)


第4项:无物体的置信度损失(重点!)

$$
\lambda_{\text{noobj}} \sum_{i=0}^{S^2} \sum_{j=0}^{B} \mathbb{1}_{ij}^{\text{noobj}} (C_i - \hat{C}_i)^2
$$

含义:让不负责任何物体的框的置信度趋近于 0。

  • $\mathbb{1}{ij}^{\text{noobj}} = 1 - \mathbb{1}{ij}^{\text{obj}}$
  • 总共有 49 网格 × 2 框 = 98 个预测框
  • 但一张图通常只有 2~5 个物体 → 只有 2~5 个框是“有物体”的
  • 剩下 90+ 个框都是背景!

⚠️ 问题:如果不对这些背景框惩罚,模型会胡乱预测高置信度框(全是假阳性)。

🔧 解决方案:

  • 计算它们的 loss(希望 $C_i = 0$)
  • 但乘以一个小权重 $\lambda_{\text{noobj}} = 0.5$
    防止负样本(背景)主导总损失(否则 loss 全被背景控制,物体学不好)

第5项:分类损失

$$
\sum_{i=0}^{S^2} \mathbb{1}{i}^{\text{obj}} \sum{c \in \text{classes}} (p_i© - \hat{p}_i©)^2
$$

含义:只对包含物体中心的网格,计算其类别概率误差。

  • 注意:这里没有 j(框索引)!因为 YOLOv1 中一个网格只输出一组类别概率(共享给两个框)
  • 用 L2 损失(也可以用交叉熵,但原论文用 L2)
  • 如果网格没物体,不计算分类 loss

💡 举例:
网格 (2,5) 中心有“猫” → $\hat{p}(\text{cat}) = 1$,其他类=0
模型预测 $p(\text{cat}) = 0.8$ → 误差 = (0.8 - 1)² = 0.04


🧩 为什么这样设计?总结三大智慧

设计 目的
$\lambda_{\text{coord}} = 5$ 强调定位精度比分类更重要(检测任务的核心是“在哪”)
$\lambda_{\text{noobj}} = 0.5$ 平衡正负样本(98 个框 vs 3 个物体),防止背景噪声淹没信号
√w, √h 让小物体和大物体的定位误差“公平竞争”,提升小物体检测能力

🖼️ 举个完整例子(一张图有 1 个物体)

  • 图像:448×448,含 1 只狗
  • 狗的中心落在网格 #23(即第 23 个网格)
  • 该网格的两个预测框:Box A(IoU=0.7),Box B(IoU=0.4)→ 选 A 负责

那么损失计算如下:

损失项 是否计算? 说明
Box A 的 (x,y) 误差 $\mathbb{1}_{23,0}^{\text{obj}} = 1$
Box A 的 (√w, √h) 误差 同上
Box A 的 confidence 误差 目标 = 0.7
Box B 的所有误差 不负责,$\mathbb{1}_{23,1}^{\text{obj}} = 0$
网格 #23 的分类误差 $\mathbb{1}_{23}^{\text{obj}} = 1$
其他 48 个网格的 96 个框 ✅(仅 confidence) $\mathbb{1}_{ij}^{\text{noobj}} = 1$,希望 confidence≈0

✅ 总结一句话

YOLOv1 的损失函数是一个精心加权的多任务回归损失,它通过:

  • 只让正确的网格和框学习
  • 放大定位和小物体的误差
  • 抑制背景框的置信度

实现了端到端的统一检测训练。

如果你现在再回头看公式,应该能看懂每一项在“惩罚谁”、“为什么惩罚”、“罚多重”了!