目标检测算法:Faster-RCNN论文解读

目标检测算法:Faster-RCNN论文解读

前言

​ 其实网上已经有很多很好的解读各种论文的文章了,但是我决定自己也写一写,当然,我的主要目的就是帮助自己梳理、深入理解论文,因为写文章,你必须把你所写的东西表达清楚而正确,我认为这是一种很好的锻炼,当然如果可以帮助到网友,也是很开心的事情。

说明

​ 如果有笔误或者写错误的地方请指出(勿喷),如果你有更好的见解也可以提出,我也会认真学习。

原始论文地址

点击这里,或者复制链接

https://arxiv.org/abs/1506.01497

目录结构

1. 文章内容概述:

​ 目前的检测算法都依赖于“region proposal”算法,虽然SSP-net、Fast-RCNN等技术的进步缩短了检测网络运行的时间,但同时也暴漏了region proposal的耗时。

​ 因此,作者在Fast-RCNN基础上引入了RPN,通过在原来的CNN结构上添加几个卷积层,在实现共享权值的同时,几乎实现了无成本的区域建议方法。

2. Faster-RCNN流程介绍:

​ 论文原图中的流程如下图:

在这里插入图片描述

​ 当然,如果你仅仅是想要知道流程怎么样,对其内部不感兴趣的话,可以直接看此图,流程如下:

  • 首先,输入一张图片
  • 然后,将这张图片送给CNN架构,其输出一个特征图
  • 然后,利用RPN网络产生一些区域建议框
  • 其次,将区域建议框映射到特征图上,并使用ROI Pooling方法产生固定长度的输出
  • 然后,把ROI Pooling输出的值用于回归和分类即可

​ **但是,上面的流程其实非常的简短并且有些地方充满疑惑性。**因此,网上有前辈们根据pytorch官方代码和论文,总结了一张详细的流程图(来自参考资料1):

在这里插入图片描述

​ 对上图进行简单的说明:

  • 首先,将图片缩放到指定尺寸,然后送给去除了全连接层的VGG16,其输出一张特征图

问题:为什么要缩放到指定尺寸?

​ 明明有了ROI Pooling(无论输入,输出大小固定),为什么还需要缩放到指定尺寸。这是当时的实现工具所限制的,当时还没有如tensorflow、pytorch等简单的框架,因此考虑到方便,还是将图片缩放到同样的尺寸,方便处理。

  • 然后,特征图分两步走,一步是送进RPN,一步是送给ROI Pooling

    • RPN部分:首先,根据特征图遍历生成所谓的anchors;然后将特征图经历一个3*3卷积层,再分别进行回归(校准anchor)和分类(判别anchors)。上图RPN结构中,上面路径为分类,下面路径为回归
  • 接着,利用RPN生成的建议框(就是上面校准后的anchors)映射于特征图上,并将每个建议框对应的特征图内容(大小不同)提取出进行ROI Pooling操作,输出对应的ROI Pooling特征向量(长度相同)。

  • 最后,将ROI Pooling特征向量进行两个全连接操作,然后进行分类和回归(softmax)

下面,对上面的关键知识点进行解读:

3. Anchor/Anchor boxes:

​ RPN是Faster-RCNN中最为重要的结构,我们首先需要明白其目的:生成好的区域建议框。

​ 那么,看论文原图:

在这里插入图片描述

首先,对上图进行简单说明,然后再细细解读细节。上图中的conv feature map,就是CNN架构最后输出的特征图,红色的框,称之为滑动窗口(sliding window)。即,在特征图上滑动一个窗口,这个窗口将特征图的n*n(图中为3*3)作为输入,将最后的输出(图中的256-d)再送给分类与回归。

其实,不难看出,这个所谓的滑动窗口,就是一个3*3卷积层,没什么好神奇的。这也对应了最开始Faster-RCNN的3*3卷积层。

解释:上面的数字含义

​ 256-d,这是维度的意思。因为在Faster-RCNN论文中,CNN架构采取的是ZF模型,该模型最后一个卷积层输出的特征图通道数就是256维。同理,如果换为VGG16,那么此处应该为512-d。

​ k anchor boxes,需要知道的是anchor boxes就是我们的区域建议框,不过此时的区域建议框还是很粗暴的,因为它没有经过分类和回归的修正。其中的k表示数量的意思。

​ 2k scores和4k coordinate,一个是分类的得分(概率值),一个是坐标值。2k,表示一个框2个值(正例概率+负例概率),那么k个框,就是2k个值。同理,4k,表示一个框4个坐标值(x+y+w+h),那么k个框就是4k个值。

解释:anchor boxes是如何产生的

​ 首先,Anchor一般指框的中心,而Anchor Boxex才指的是框。

​ 从上图其实不难看出,k个anchor boxes的中心都用蓝色虚线对应了滑动窗口的中心,**这意味着滑动窗口(可移动的)每个中心都会产生k个anchor boxes。我们又知道,滑动窗口其实就是一个3*3卷积层,而特征图就是其输入,那么意味着特征图每个点都会产生k个anchor boxes。**在原文中,k取9。

​ 上面解决了第一个问题,即anchor boxes如何产生的。那么,还有一个问题,每个点都会产生k个anchor boxes,这个anchor boxes有没有什么要求?其实这个是人为定的,而在论文中,作者认为采取三个比例和三个长宽比,这样就会产生3*3=9个框,如下图所示(自己画的):(具体到代码,一般会给定一个基础的anchor,后面的则根据比例等生成)

在这里插入图片描述

解释:一张特征图上的Anchor boxes数量

​ 我们假设原图大小为400*400,而CNN架构采取VGG16,那么可以知道原图经过VGG16后,得到的特征图其实缩小了16倍(4个池化层,每个缩小2倍)。

​ 那么,总共的Anchor boxes数量为:

(400/16)*(400/16)*9 = 5625

​ 问题来了,五千多个的建议框实在太多了。作者于是精选了256个合适的建议框,并且正例和负例的比列为1:1。

​ 怎样判断建议框是否合适呢?满足下列条件即可:

  • IOU > 0.7的建议框为正例
  • IOU最大的建议框为正例
  • IOU < 0.3的建议框为负例
  • 处于0.3和0.7之间的建议框直接忽略

解释:NMS与越界剔除

​ 获取到建议框后,仍然需要进行NMS(非极大值抑制,不清楚的可以看我RCNN论文解读)和越界剔除(即建议框超出了原图,需要去掉)。

解释:下图中的18和36是怎么得到的?

在这里插入图片描述

​ 首先,18和36都是代表通道数或维数。36=4*9,即9个框,每个框4个坐标值,其对应的数据格式应该为:

[batch_size,4*9,W,H]

​ 18=2*9,就是9个框,每个框对应2个类别值(正例或负例),其对应的数据格式为:

[batch_size,2*9,W,H]

问题:anchor boxes产生在原图还是特征图?

​ 其实从我个人的角度来说,anchor boxes产生在原图和特征图上区别不大。比如产生在原图,那么你可以通过除以16来映射到特征图上(VGG16),产生在特征图上同理。

​ 但是,从实际角度来说,anchor boxes是产生在原图的。为什么这么说?因为我们需要计算anchor boxes与真实框的IOU值,这从一定程度上已经告诉我们了它就是产生在原图的(除非你想多计算一步,多浪费点资源)。

RPN中的回归怎么实现?

​ 这个怎么讲呢,就是常见的框回归问题,几乎和RCNN中的框回归一模一样,没什么特殊的地方,如果你感兴趣,可以打开我的博客主页,找到RCNN论文解读中的部分。或者直接复制下面链接:

https://blog.csdn.net/weixin_46676835/article/details/129929232

4. 损失函数:

​ Faster-RCNN的损失函数,中规中矩,和Fast-RCNN变换不大。

​ 具体公式如下:

在这里插入图片描述

​ 其中:

  • i表示在某一个batch中的第i个anchor boxes
  • Pi表示anchor框包围的对象为不同类的概率(比如总共20各类,分别为各类的概率值)
  • Pi*取{0,1},其值由i这个anchor是否为正例决定,为正例则取1,否则取0。这意味着只有该值取1时,回归才计入损失,也即只有包含对象的框才值得计入损失,否则没啥意义。
  • ti表示第i个anchor对应的4个坐标值,ti*为真实框的坐标值
  • 在论文中,Ncls取batch_size的数目(假设为256),Nreg取特征图的大小(假设输入图片600*1000,VGG16架构,则特征图大小约为2400),而λ是用来平衡两者的大小关系,此时取2400/256,约为10。
  • 在代码中,直接让Ncls和Nreg都取batch_size大小,这样λ直接取1即可,方便简单。

​ 而Lcls则是常用的分类损失函数,即交叉熵损失函数:

在这里插入图片描述

​ 而Lreg则是目标检测领域常用的平滑L1损失函数,即:

在这里插入图片描述

5. Faster-RCNN训练:

​ 现在想想,Faster-RCNN的训练流程其实和它的Anchor一样重要。

​ 其实,在如何训练Faster-RCNN上,作者提出了三种方法,分别是4步交替训练、近似联和训练、非近似联合训练。

​ 简单说说这三个方法:

  • 交替训练:作者采取的方法,后面详细说
  • 近似联合训练:即将RPN和Fast-RCNN训练时合并为一个网络。前向传递时RPN生成区域建议框,然后这些区域建议框再送给Fast-RCNN。反向传递时,就正常反向传播,只是对于共享的卷积层(即CNN架构部分),将RPN损失和Fast-RCNN损失合并。
    • 这个方法容易实现,但是忽略了anchor boxes坐标的导数值,即反向传播时不考虑anchor boxes的导数(这也是近似的由来)。
  • 非近似联合训练:非常复杂,不考虑

作者最终选择了交替训练的方法来训练Faster-RCNN,具体流程如下:

  • 首先,肯定是把CNN架构(这里设为VGG)放在ImageNet上训练好
  • 然后,VGG加上RPN网络部分(权值/卷积共享思想),开始训练RPN,其生成一系列的区域建议框
  • 第一次训练Faster-RCNN(不包含RPN部分,更加准确的来说是训练Fast-RCNN)
  • 再次训练RPN,得到新的区域建议框
  • 第二次训练Faster-RCNN(不包含RPN部分,更加准确的来说是训练Fast-RCNN)
  • …(迭代重复直至收敛,作者这里发现两次左右就收敛了)

6. 总结:

​ Faster-RCNN是两阶段检测的集大成之作,吸收了前面的所有精华。其主要的贡献在于:

  • 提出了RPN结构,并巧妙利用了卷积共享的方法减少计算量
  • 提出了anchor的思路
  • 交替训练方法

猜你喜欢

转载自blog.csdn.net/weixin_46676835/article/details/131049773