超全面目标检测算法综述

声明:本文大部分参考机器之心的文章《从RCNN到SSD,这应该是最全的一份目标检测算法盘点》,仅作为学习之用,如若侵权,请马上联系我删除。(另外,强烈安利机器之心,文章质量都非常高!)

=======================================================================

目标检测是很多计算机视觉任务的基础,不论我们需要实现图像与文字的交互还是需要识别精细类别,它都提供了可靠的信息。本文对目标检测进行了整体回顾,第一部分从 RCNN 开始介绍基于候选区域的目标检测,包括 Fast R-CNN、Faster R-CNN 和 R-FCN 等;第二部分则重点讨论了包括 YOLO、SSD 和 RetinaNet 等在内的单次检测器,它们都是目前最为优秀的方法。

目标检测目前有 one-stage 和 two-stage 两种,two-stage 指的是检测算法需要分两步完成,首先需要获取候选区域,然后进行分类,比如R-CNN系列;与之相对的是 one-stage 检测,可以理解为一步到位,不需要单独寻找候选区域,典型的有SSD/YOLO。

一、基于候选区域的目标检测

1. 滑动窗口检测器

自从 AlexNet 获得 ILSVRC 2012 挑战赛冠军后,用 CNN 进行分类成为主流。一种用于目标检测的暴力方法是从左到右、从上到下滑动窗口,利用分类识别目标。为了在不同观察距离处检测不同的目标类型,需要使用不同大小和宽高比的窗口。

滑动窗口(从左到右,从上到下)

我们根据滑动窗口从图像中剪切图像块。由于很多分类器只取固定大小的图像,因此这些图像块是经过变形转换的。但是,这不影响分类准确率,因为分类器可以处理变形后的图像。

将图像变形转换成固定大小的图像

变形图像块被输入 CNN 分类器中,提取出 4096 个特征。之后,我们使用 SVM 分类器识别类别和该边界框的另一个线性回归器。

滑动窗口检测器的系统工作流程图

下面是伪代码。我们创建很多窗口来检测不同位置的不同目标,要提升性能,一个显而易见的办法就是减少窗口数量。

for window in windows:
    patchs = get_patch(image, window)
    results = detector(patchs)
2. R-CNN

实际上,更实用的方法是候选区域(Region Proposals )方法来获取感兴趣的区域(ROI)。选择性搜索(Selective Search )就是一种典型的候选区域方法。算法原理如下:首先将每个像素作为一组。然后,计算每一组的纹理,并将两个最接近的组结合起来。但是为了避免单个区域吞噬其他区域,我们首先对较小的组进行分组。我们继续合并区域,直到所有区域都结合在一起。下图第一行展示了如何使区域增长,第二行中的蓝色矩形代表合并过程中所有可能的 ROI。与寻找几乎个区域比起来,这种方法要高效的多。

选择性搜索算法过程

R-CNN 利用候选区域方法创建了约 2000 个 ROI。这些区域被转换为固定大小的图像,并分别送到卷积神经网络中。之后使用SVM对区域进行分类,使用线性回归损失来校正边界框,以实现目标分类并得到边界框。以下是 R-CNN 整个系统的流程图:

通过使用更少且更高质量的 ROI,R-CNN 要比滑动窗口方法更快速、更准确。伪代码如下:

ROIs = region_proposal(image)
for ROI in ROIs
    patch = get_patch(image, ROI)
    results = detector(patch)
3. Fast R-CNN

R-CNN 需要非常多的候选区域以提升准确度,但其实有很多区域是彼此重叠的。如果我们有 2000 个候选区域,且每一个都需要独立地馈送到 CNN 中,那么对于不同的 ROI,我们可能需要重复提取很多次特征。因此 R-CNN 的训练和预测速度非常慢。

此外,CNN 中的特征图以一种密集的方式表征空间特征,那么我们能直接使用特征图代替原图来检测目标吗?答案是肯定的。

直接利用特征图计算 ROI

Fast R-CNN 使用CNN网络先提取整个图像的特征,而不是对每个图像块提取多次。然后,我们可以将创建候选区域的方法直接应用到提取到的特征图上。例如,Fast R-CNN 选择了 VGG16 中的卷积层 conv5 来生成 ROI区域在对应的特征图上的映射特征图块,并用于目标检测任务中。我们使用 ROI 池化将特征图块转换为固定的大小,并送到全连接层进行分类和定位。因为 Fast-RCNN 不会重复提取特征,所以它能显著地减少处理时间。

将候选区域直接应用于特征图,并使用 ROI 池化将其转化为固定大小的特征图块

以下是 Fast R-CNN 的流程图:

ROI 池化
因为 Fast R-CNN 使用全连接层,所以我们应用 ROI 池化将不同大小的 ROI 转换为固定大小。比如我们将 8×8 特征图转换为预定义的 2×2 大小:

输入特征图(左上),输出特征图(右下),ROI (右上,蓝色框)

左上角:输入特征图;
右上角:将 ROI(蓝色区域)与特征图重叠;
左下角:将 ROI 拆分为目标维度。例如,对于 2×2 目标,我们将 ROI 分割为 4 个大小相似或相等的部分;
右下角:找到每个部分的最大值,得到变换后的特征图。

按上述步骤得到一个 2×2 的特征图块,可以送至分类器和边界框回归器中。使用softmax损失进行分类;使用回归损失比如平滑L1损失校正包围框。总损失是两部分的和,然后反向传播进行训练。Fast R-CNN 最重要的一点就是包含特征提取器、分类器和边界框回归器在内的整个网络能通过多任务损失函数进行端到端的训练,这种多任务损失即结合了分类损失和定位损失的方法,大大提升了模型准确度。

在下面的伪代码中,计算量巨大的特征提取过程从 For 循环中移出来了,因此速度得到显著提升。Fast R-CNN 的训练速度是 R-CNN 的 10 倍,预测速度是后者的 150 倍。

feature_maps = process(image)
ROIs = region_proposal(feature_maps)
for ROI in ROIs
    patch = roi_pooling(feature_maps, ROI)
    results = detector2(patch)
4. Faster R-CNN

Fast R-CNN 依赖于外部候选区域方法,如选择性搜索。但这些算法在 CPU 上运行且速度很慢。在测试中,Fast R-CNN 需要 2.3 秒来进行预测,其中 2 秒用于生成 2000 个 ROI。因此区域生成的计算成为整个检测网络的瓶颈。

与其使用固定的算法得到候选区域,不如让网络自己学习自己的候选区域应该是什么。因此,Faster R-CNN 采用与 Fast R-CNN 相同的设计,只是它用区域生成网络(Region Proposal Network,RPN)代替了候选区域方法。新的候选区域网络(RPN)在生成 ROI 时效率更高,并且以每幅图像 10 毫秒的速度运行。

Faster R-CNN 的流程图与 Fast R-CNN 基本相同,只是使用RPN代替了原来的外部候选区域方法

RPN
区域生成网络(RPN)将前面卷积网络的输出特征图作为输入,比如VGG16的conv5特征图。它在特征图上滑动一个 3×3 的卷积核,以使用卷积网络构建与类别无关的候选区域。使用VGG网络提取特征的话,每个 3x3 区域会得到一个512维的特征向量,然后送到两个独立的全连接层,以预测边界框和两个目标分数(是目标或者不是目标)。我们其实可以使用回归器计算单个 目标分数,但为简洁起见,Faster R-CNN 使用只有两个类别的分类器:即带有目标的类别和不带有目标的类别。

对于特征图中的每一个位置,RPN 会做 k 次预测。因此,RPN 将输出 4×k 个坐标和每个位置上 2×k 个得分。下图展示了 8×8 的特征图,且有一个 3×3 的卷积核执行运算,它最后输出 8×8×3 个 ROI(其中 k=3)。下图(右)展示了单个位置的 3 个候选区域。

上图每个位置有 3 种猜想,稍后我们将予以完善。由于只需要一个正确猜想,因此我们最初的猜想最好涵盖不同的形状和大小。因此,Faster R-CNN 不会创建随机边界框。相反,它会预测一些与左上角名为锚点的参考框相关的偏移量(如𝛿x、𝛿y)。要对每个位置进行 k 个预测,我们需要以每个位置为中心的 k 个锚点。这些锚点是精心挑选的,因此它们是多样的,且覆盖具有不同比例和宽高比的现实目标。这使得我们可以以更好的猜想来指导初始训练,并允许每个预测专门用于特定的形状。每个预测与特定锚点相关联,但不同位置共享相同形状的锚点。

Faster R-CNN 使用更多的锚点。它部署 9 个锚点框:3 个不同宽高比的 3 个不同大小的锚点框。每一个位置使用 9 个锚点,每个位置会生成 2×9 个目标分数和 4×9 个坐标。

伪代码:

feature_maps = process(image)
ROIs = rpn(feature_maps)
for ROI in ROIs
    patch = roi_pooling(feature_maps, ROI)
    class_scores, box = detector(patch) 
    class_probabilities = softmax(class_scores)

这部分详细的内容可以参考:Faster R-CNN:使用RPN实时目标检测

5. F-RCN

R-FCN 通过减少每个 ROI 所需的工作量实现加速。上面基于区域的特征图与 ROI 是独立的,可以在每个 ROI 之外单独计算。剩下的工作就比较简单了,因此 R-FCN 的速度比 Faster R-CNN 快。

feature_maps = process(image)
ROIs = region_proposal(feature_maps)         
score_maps = compute_score_map(feature_maps)
for ROI in ROIs
    V = region_roi_pool(score_maps, ROI)     
    class_scores, box = average(V)                   # Much simpler!
    class_probabilities = softmax(class_scores)

二、One-Stage 目标检测

这部分我们将对单次目标检测器(包括 SSD、YOLO、YOLOv2、YOLOv3)进行综述。我们将分析 FPN 以理解多尺度特征图如何提高准确率,特别是小目标的检测,其在单次检测器中的检测效果通常很差。然后我们将分析 Focal loss 和 RetinaNet,看看它们是如何解决训练过程中的类别不平衡问题的。

one-stage检测器

Faster R-CNN 中有一个专用的候选区域网络RPN。基于区域的检测器是很准确的,但需要付出代价。Faster R-CNN 在 PASCAL VOC 2007 测试集上每秒处理 7 帧的图像(7 FPS)。作为替代,我们是否需要一个分离的候选区域步骤?我们可以直接在一个步骤内得到边界框和类别吗?

feature_maps = process(image)
results = detector3(feature_maps) # No more separate step for ROIs

让我们再看一下滑动窗口检测器。我们可以通过在特征图上滑动窗口来检测目标。对于不同的目标类型,我们使用不同的窗口类型。以前的滑动窗口方法的致命错误在于使用窗口作为最终的边界框,这就需要非常多的形状来覆盖大部分目标。更有效的方法是将窗口当做初始猜想,这样我们就得到了从当前滑动窗口同时预测类别和边界框的检测器。

基于滑动窗口进行预测

这个概念和 Faster R-CNN 中的锚点很相似。然而,单次检测器会同时预测边界框和类别。例如,我们有一个 8 × 8 特征图,在每个位置,我们有 k 个锚点(锚点是固定的初始边界框猜想),一个锚点对应一个特定位置。我们使用相同的锚点形状仔细地选择锚点和每个位置,并在每个位置做出 k 个预测,即总共有 8 × 8 × k 个预测结果。

使用 3 个锚点在每个位置做出 3 个预测

以下是 4 个锚点(绿色)和 4 个对应预测(蓝色),每个预测对应一个特定锚点。

4 个预测,每个预测对应一个锚点

在 Faster R-CNN 中,我们使用卷积核来做 6个参数的预测:4 个参数对应某个锚点的预测边框,2个参数对应 objectness 置信度得分。因此 3× 3× D × 6 卷积核将特征图从 8 × 8 × D 转换为 8 × 8 × 6。

使用 3x3 卷积核计算预测

在单次检测器中,卷积核还预测 C 个类别概率以执行分类(每个概率对应一个类别,包含背景)。因此我们应用一个 3× 3× D × 25 卷积核将特征图从 8 × 8 × D 转换为 8 × 8 × 25 (C=20,(dx, dy, dh, dw, confidence)4个边框参数,1个置信度)。

每个位置做出 k 个预测,每个预测有 25 个参数

单次检测器通常需要在准确率和实时处理速度之间进行权衡。它们在检测太近距离或太小的目标时容易出现问题。在下图中,左下角有 9 个圣诞老人,但某个单次检测器只检测出了 5 个。

2.1 SSD

SSD(Single-Shot MultiBox Detector),使用 VGG19 网络作为特征提取器(和 Faster R-CNN 中使用的 CNN 一样)的单次检测器。我们在该网络之后添加自定义卷积层(蓝色),并使用卷积核(绿色)执行预测。

同时对类别和位置执行单次预测

然而,卷积层降低了空间维度和分辨率。因此上述模型仅可以检测较大的目标。为了解决该问题,我们从多个特征图上执行独立的目标检测。

使用多尺度特征图用于检测

以下是特征图图示。

image

SSD 使用卷积网络中较深的层来检测目标。如果我们按接近真实的比例重绘上图,我们会发现图像的空间分辨率已经被显著降低,且可能已无法定位在低分辨率中难以检测的小目标。如果出现了这样的问题,我们需要增加输入图像的分辨率。

2.2 YOLO / v2 / v3

YOLO (You Only Look Once)是另一种单次目标检测器。YOLO 在卷积层之后使用了 DarkNet 来做特征检测。

然而,它并没有使用多尺度特征图来做独立的检测。相反,它将特征图部分平滑化,并将其和另一个较低分辨率的特征图拼接。例如,YOLO 将一个 28 × 28 × 512 的层重塑为 14 × 14 × 2048,然后将它和 14 × 14 ×1024 的特征图拼接。之后,YOLO 在新的 14 × 14 × 3072 层上应用卷积核进行预测。

YOLO v2做出了很多实现上的改进,比如使用BN层、使用高分辨率图像微调分类模型、采用Anchor Boxes、约束预测边框的位置等,将 mAP 值从第一次发布时的 63.4 提高到了 78.6。YOLO9000 可以检测 9000 种不同类别的目标。

YOLO v3主要的改进有:调整了网络结构;利用多尺度特征进行对象检测;对象分类用logistic取代了softmax。下面主要介绍一下YOLO v3。(参考文章:YOLO v3深入理解

网络架构

在基本的图像特征提取方面,YOLO v3采用了称之为Darknet-53的网络结构(含有52个卷积层1个全连接层),它借鉴了残差网络residual network的做法,在一些层之间设置了快捷链路(shortcut connections)。DarkNet-53 主要由 3 × 3 和 1× 1 的卷积核以及类似 ResNet 中的快捷链路构成。相比 ResNet-152,DarkNet 有更低的 BFLOP(十亿次浮点数运算),但能以 2 倍的速度得到相同的分类准确率。

上图的Darknet-53网络采用2562563作为输入,最左侧那一列的1、2、8等数字表示多少个重复的残差组件。每个残差组件有两个卷积层和一个快捷链路,示意图如下:

残差组件

特征金字塔网络(FPN)——利用多尺度特征进行检测

YOLO v2曾采用passthrough结构来检测细粒度特征,在YOLO v3更进一步采用了3个不同尺度的特征图来进行对象检测。

结合上图看,卷积网络在79层后,经过下方几个黄色的卷积层得到一种尺度的检测结果。相比输入图像,这里用于检测的特征图有32倍的下采样。比如输入是416x416的话,这里的特征图就是13x13了。由于下采样倍数高,这里特征图的感受野比较大,因此适合检测图像中尺寸比较大的对象。

为了实现细粒度的检测,第79层的特征图又开始作上采样(从79层往右开始上采样卷积),然后与第61层特征图融合(Concatenation),这样得到第91层较细粒度的特征图,同样经过几个卷积层后得到相对输入图像16倍下采样的特征图。它具有中等尺度的感受野,适合检测中等尺度的对象。

最后,第91层特征图再次上采样,并与第36层特征图融合,最后得到相对输入图像8倍下采样的特征图。它的感受野最小,适合检测小尺寸的对象。

上面使用不同尺寸特征图进行预测的网络称为特征金字塔网络(FPN),是一种旨在提高准确率和速度的特征提取器。数据流如下:

FPN

FPN 由自下而上和自上而下路径组成。其中自下而上的路径是用于特征提取的常用卷积网络。空间分辨率自下而上地下降。当检测到更高层的结构,每层的语义值增加。

FPN中的特征提取

SSD 通过多个特征图完成检测。但是,最底层不会被选择执行目标检测。它们的分辨率高但是语义值不够,导致速度显著下降而不能被使用。SSD 只使用较上层执行目标检测,因此对于小的物体的检测性能较差。

FPN 提供了一条自上而下的路径,从语义丰富的层利用上采样构建高分辨率的层。

自上而下重建空间分辨率

虽然该重建层的语义较强,但在经过所有的上采样和下采样之后,目标的位置不精确。在重建层和相应的特征图之间添加横向连接可以使位置侦测更加准确。

增加跳过连接

FPN 可以结合 Fast R-CNN 或 Faster R-CNN。在 FPN 中,我们生成了一个特征图的金字塔,然后用 RPN(来生成 ROI。基于 ROI 的大小,我们选择最合适尺寸的特征图层来提取特征块。

9种尺度的 anchor boxes

随着输出的特征图的数量和尺度的变化,先验框的尺寸也需要相应的调整。YOLO2已经开始采用K-means聚类得到先验框的尺寸,YOLO3延续了这种方法,为每种下采样尺度设定3种先验框,总共聚类出9种尺寸的先验框。在COCO数据集这9个先验框是:(10x13),(16x30),(33x23),(30x61),(62x45),(59x119),(116x90),(156x198),(373x326)。

分配上,在最小的13x13特征图上(有最大的感受野)应用较大的先验框(116x90),(156x198),(373x326),适合检测较大的对象。中等的26x26特征图上(中等感受野)应用中等的先验框(30x61),(62x45),(59x119),适合检测中等大小的对象。较大的52x52特征图上(较小的感受野)应用较小的先验框(10x13),(16x30),(33x23),适合检测较小的对象。

感受一下9种先验框的尺寸,下图中蓝色框为聚类得到的先验框。黄色框式ground truth,红框是对象中心点所在的网格。

分类softmax改成logistic

预测对象类别时不使用softmax,改成使用logistic的输出进行预测。

输入映射到输出

不考虑神经网络结构细节的话,总的来说,对于一个输入图像,YOLO v3将其映射到3个尺度的输出张量,代表图像各个位置存在各种对象的概率。

我们看一下YOLO v3共进行了多少个预测。对于一个416x416的输入图像,在每个尺度的特征图的每个网格设置3个先验框,总共有 13x13x3 + 26x26x3 + 52x52x3 = 10647 个预测。每一个预测是一个(4+1+80)=85维向量,这个85维向量包含边框坐标(4个数值),边框置信度(1个数值),对象类别的概率(对于COCO数据集,有80种对象)。

对比一下,YOLO v2采用13x13x5 = 845个预测,YOLO v3的尝试预测边框数量增加了10多倍,而且是在不同分辨率上进行,所以mAP以及对小物体的检测效果有一定的提升。

2.3 RetianNet

RetianNet是基于 ResNet、FPN以及利用 Focal loss 构建的 。

RetinaNet

Focal Loss

类别不平衡会损害性能。SSD 在训练期间重新采样目标类和背景类的比率,这样它就不会被图像背景淹没。Focal loss(FL)采用另一种方法来减少训练良好的类的损失。因此,只要该模型能够很好地检测背景,就可以减少其损失并重新增强对目标类的训练。我们从交叉熵损失 (Cross Entroy Loss)开始,并添加一个权重来降低高可信度类的交叉熵。

例如,令 γ = 0.5, 经良好分类的样本的 Focal Loss 趋近于 0。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 158,736评论 4 362
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 67,167评论 1 291
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 108,442评论 0 243
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 43,902评论 0 204
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 52,302评论 3 287
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 40,573评论 1 216
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 31,847评论 2 312
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 30,562评论 0 197
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 34,260评论 1 241
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 30,531评论 2 245
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 32,021评论 1 258
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 28,367评论 2 253
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 33,016评论 3 235
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 26,068评论 0 8
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 26,827评论 0 194
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 35,610评论 2 274
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 35,514评论 2 269