focal_loss

code

paper

摘要:

目前目标检测精度最高的是RCNN引导的两阶段的方法,相反,一阶段的方法更快更简单,但是精度落后很多. 我们发现这种根本原因是因为在训练过程中正负样本不均衡。本文提出了改变标准交叉熵损失:降低易分样本的损失权重的方法来解决这种类别不平衡方法。为了检验方法的有效性,还提出了一个RetinaNet,速度可以和一阶段的检测器相媲美而且检测精度也很高。

处理样本不均衡的常用方法:

  • SSD+hard negative mining(OHNM):匹配default box之后根据box的confidence排序得到正样本三倍数量的负样本(正负比例1:3)
  • Fast RCNN+ONEM:引入read only层先forward一遍样本,选取loss最大的前N个重新送入ROIpooling,仅解决了easy example的问题。
  • Class Balanced Loss:分别计算正负样本的loss,引入权重来实现平衡,主要考虑类间平衡。
  • Focal Loss:改进的CE loss,动态调整参数均衡正负样本不均衡。

RetinaNet-101 = ResNet-101-FPN

引言

​ 两阶段目标检测算法精度一直在各个榜单遥遥领先,本文就是提出了一个一阶段的检测器,并且精度能够媲美二阶段目标检测器,比如FPN,或者Faster RCNN的变体Mask RCNN.本文认为,妨碍一阶段检测器达到较高精度的主要障碍是,类别不平衡。

RCNNs中的正负样本均衡的原因

​ 在RCNN这样的检测器中,类别不平衡问题已经被两阶段级联和采样的启发式方法解决了。

  • 区域提议阶段(selective search,edgebox,deepmask,RPN)阶段可以迅速降低候选目标区域的数目(1-2k),过滤掉大部分的背景sample。
  • 分类阶段,通过启发式采样方法,比如:在mini batch中固定的正负样本比例(1:3),在线难样本挖掘(OHEM),来达到前景和背景之间的平衡。

one-stage的类别不均衡原因

  • one-stage检测器需要处理在整张图上采样下来的大量候选目标区域,实际中,因为需要遍历各个空间位置,尺度,和纵横比,这个数量会达到大约100k。In practice this often amounts to enumerating ∼100k locations that densely cover spatial positions,scales, and aspect ratios.
  • 虽然one-stage也用了启发式的采样方法如(boostrapping),比如SSD中使用OHEM控制正负样本比例在1:3左右,仍然是没用,因为训练过程仍然被易分的背景样例所主导。While similar sampling heuristics may also be applied, they are inefficient as the training procedure is still dominated by easily classified background examples.

本文方法

​ 本文提出了一种新的损失函数方法,能够动态放缩交叉熵损失。如图1.当正确类别的系数上升时,这个放缩因子就会降到0.另外这个放缩因子能够自动的降低易分样本在训练中的贡献,并且迅速关注那些难分样本。

​ focal-loss的具体形式不重要,别的形式也能达到相似的效果。

👀 作者也没说自己的方法为什么比OHEM之类的好。。。。。

RetinaNet

one-stage detector,网络内部包含特征金字塔和anchor的使用。backbone是ResNet101-FPN在COCO测试集达到了39.1的AP并且速度每秒5帧,超过了所有一阶段、二阶段的单模型检测器。如图2.

Related work

Class Imbalance

​ 所有一阶段检测器,包括增强detector(boosted detector),DPM或者SSD都面临严重的类别不平衡问题。每张图需要处理$10^4-10^5$候选区域而只有少数是真正包含目标的。这导致了两个问题:

  1. 训练没有效率:大部分位置都是负样本,导致无效的学习。
  2. 负样本会压倒训练,导致产生不了模型。

常见的方法就是:

  1. 按照class比例加权重:最常处理类别不平衡问题的方式
  2. OHEM:只保留loss高的那些样本,完全忽略掉简单样本
  3. 难样本挖掘+按class比例sample:在前者基础上,在保证正负样本3:1

我们的方法就是能够自动处理这种不均衡,允许我们在所有样本上训练,并且过程中没有压倒性的负样本损失和梯度。

Robust Estimation

robust loss:减少了异常点outlier的贡献,通过降低hard example的损失权重。

focal loss:降低了inliers(easy example)的权重,因此他们对整体损失的贡献就降低了即使他们的数目很多。

Focal loss

正负样本不均衡,比如1:1000.

二元分类的交叉熵:
$$
CE(p,y)=\begin{cases}-log(p)\qquad if \quad y=1 \ -log(1-p)\qquad otherwise\end{cases}\qquad(1)
$$
以上式子中,$y\in{\pm1}$表示ground truth的标签。$p\in[0,1]$是模型估计$y=1$的类别概率。定义$p_t$如下:
$$
p_t=\begin{cases}p\qquad if\quad y=1\1-p\qquad otherwise\qquad(2)\end{cases}
$$

$$
CE(p,y)=CE(p_t)=-log(p_t)
$$

就是图1上面的那个蓝色的线。即使:

易分样本($p_t>>0.5)$

也会有很大的损失。当大量易分样本叠加时,这些损失会最终压倒那些稀少的样本。

平衡交叉熵

​ 引入一个权重因子$\alpha\in[0,1]$给类别1,$1-\alpha$给类别-1.实际操作中,$\alpha$通常是设置成类别频数的倒数,或者由交叉验证来设置。

$\alpha$平衡的CEloss定义如下:
$$
CE(p_t)=-\alpha_tlog(p_t)\qquad(3)
$$

Focal Loss Definition

易分的负样本包含了损失的绝大部分,主导了梯度。虽然$\alpha$平衡了正负样本的重要性,但是他没能区分简单样本和难样本了。

Easily classified negatives comprise the majority of the loss and dominate the gradient.
While α balances the importance of positive/negative examples, it does not differentiate between easy/hard examples.

我们提出的方法能够重构这个损失,降低易分样本的权重,专注于难分负样本的训练。Instead,we propose to reshape the loss function to down-weight easy examples and thus focus training on hard negatives.

引入调制因子$(1-p_t)^{\gamma}$可调的focusing 参数$\gamma\ge0$.
$$
\textbf{FL}(p_t)=-(1-p_t)^{\gamma}log(p_t)
$$
在图1中$\gamma\in[0,5]$ 可视化。

focal loss有两个属性:

  1. $p_t$很小(难样本)时,调制因子接近1,loss没有影响。当$p_t->1$(易分样本),因子接近0,loss就会比重降低。
  2. $\gamma$能够平滑的调整易分样本权重下降的速度。当$\gamma$为0,$\textbf{FL}$等同于$\textbf{CE}$ 。当$\gamma$上升,调制因子的作用也会上升。($\gamma=2$时候效果最好)。

举例:当$\gamma=2$时,$p_t=0.9$的样本的损失和交叉熵的损失比会下降100倍,$p_t=0.968$样本的损失会下降1000倍。反过来就会提升错分样本的重要性,对于$p_t\le0.5,\gamma=2$的情况,其loss会缩放到4倍。

实际操作中的focal loss形式:
$$
\textbf{FL}(p_t)=-\alpha_t(1-p_t)^{\gamma}log(p_t)\qquad(5)
$$
有了$\alpha$效果会好些,sigmod计算$p$效果也会更稳定些。

Class Imbalance and Model Initialization

训练时,数量很多的类别(background)会起主导作用,导致不稳定。为了早期训练的稳定性,作者设置了稀少类别(foreground)的值$\pi$ 这样模型估计前景的概率就比较小,比如0.01.

Class Imbalance and Two-stage Detectors

之前讲过RCNNs这样的两阶段检测器通过(1)两级级联(2)有偏好的采样 解决了样本不平衡的问题。而我们的方法直接通过损失函数来解决。

RetinaNet Detector

由一个backbone和两个特定任务的子网络组成。backbone是负责计算输入图片的特征。第一个自网络进行目标分类,第二个进行bbox 回归。

FPN

FPN增加了一个自上而下的旁路,和横向连接,因此网络可以在单一分辨率的输入图像上构建丰富的,多尺度的特征金字塔。

In brief, FPN augments a standard convolutional network with a top-down pathway and lateral connections so the network efficiently constructs a rich, multi-scale feature pyramid from a single resolution input image.

如图b.每层都能检测一个尺度,在RPN,Faster RCNN,Mask RCNN上都提高了精度。

在ResNet上构建FPN,从第3层到第7层.($P_l$比输入分辨率降低了$2^l$)。在FPN论文离所有金字塔层的通道都是256.

RetinaNet uses feature pyramid levels P3 to P7, where P3 to P5 are computed from the output of the corresponding ResNet residual stage (C3 through C5) using top-down and lateral connections just as in [20], P6 is obtained via a 3×3 stride-2 conv on C5, and P7 is computed by applying ReLU followed by a 3×3 tride-2 conv on P6. This differs slightly from [20]: (1) we don’t use the high-resolution pyramid level P2 for computational reasons, (2) P6 is computed by strided convolution instead of downsampling, and (3) we include P7 to improve large object detection. These minor modifications improve speed while maintaining accuracy .

细节如上,懒得翻译了。。。

Anchors

​ 取ResNet的$C_3,C_4,C_5$层,构建金字塔 $P_3-P_7$,每层对应的anchor面积分别为$32^2,64^2,128^2,256^2,512^2$.aspect ratio:${1:2,1:1,2:1}$ ,anchor的尺度:${2^0,2^{1/3},2^{2/3}}$.最后每层有$A=9$个anchor,能够覆盖$32-813$像素。($32\times2^0=32,512\times2^{2/3}=813$).

​ 每个anchor有:

  • 一个长度为$K$的one-hot向量,负责分类,$K$表示目标种类
  • 一个4维的向量用来回归。

分配细节:Specifically,anchors are assigned to ground-truth object boxes using an intersection-over-union (IoU) threshold of 0.5; and to background if their IoU is in [0, 0.4). As each anchor is assigned to at most one object box, we set the corresponding entry in its length K label vector to 1 and all other entries to 0. If an anchor is unassigned, which may happen with overlap in [0.4, 0.5), it is ignored during training.

Classifination Subnet:

Box Regression Subnet:

两个子网络虽然框架一样,但是参数独立。

Inference and Training

初始化

  • ResNet-50和ResNet-101都是在ImageNet1k上面的预训练模型。
  • FPN初始化使用的原文中初始化的方法。所有的卷积层(除了最后的子网络)都是初始化为$b=0,高斯权重\theta=0.01$。
  • 子网络的分类层将bias初始化为:$b=-log((1-\pi)/\pi)$,论文使用$\pi=0.01$,表示每个anchor被标记为前景的概率(confidence)为0.01.

关于bias的设置问题:

原因:

为了将训练初始阶段的anchor概率设为0.01,即当做前景的概率为0.01,即为文章中定义的难样本,这样可以保证在训练开始时,数目稀少的前景anchor能够产生较大的focal loss,防止数目较多的背景anchor在第一次迭代的时候就产生overwhelming的不稳定损失。

This initialization prevents the large number of background anchors from generating a large, destabilizing loss value in the first iteration of training.

效果如下:

优化方法

$$
Loss=sum(focal loss)+L_1Smooth
$$

只有分类层使用focalloss。

OHEM VS FL

OHEM:每个样本都对loss进行排序,再进行非极大值抑制,也就是说mini-batch里面都是loss最高的样本。和focal loss类似,OHEM更加关注错分样本,但是他完全抛弃了易分样本。效果对比如上图d

Like the focal loss,OHEM puts more emphasis on misclassified examples, but unlike FL, OHEM completely discards easy examples.

Single-model Objecto Detector vs RetinaNet