RFCN的贡献

  • 提出Position-sensitive score maps来解决目标检测的位置敏感性问题;
  • 区域为基础的,全卷积网络的二阶段目标检测框架;
  • 比Faster-RCNN快2.5-20倍(在K40GPU上面使用ResNet-101网络可以达到 0.17 sec/image

faster-rcnn的问题

      base network用于做特征的提取,生成对应的feature maps,利用rpn全卷积神经网络提取对应的RP位置,在feature maps上得到我们最后可用的ROIs,再用这些ROIs做分类和回归。第一部分用于生产feature maps的network是可以共享计算的,而第二部分的ROI-wise subnetwork是不能共享计算,这个使得检测速度变慢。

    其根本原因是分类不要具有平移不变性(translation-invariance)而检测需要平移可变性(translation-variance)。意思是一张图片不管物体的位置,颜色,纹理怎么发生发生变化,我们都能识别这个物体时某一类别,这就是平移不变性,可变性是指检测需要指出物体的位置,物体的位置发生改变时,其检测坐标也要随之改变。

对此,r-fcn提出Position-sensitive score maps来解决这个问题。

Faster -RCNN

   Faster R-CNN系列的网络都可以分成2个部分:ROI Pooling之前的共享全卷积网络和ROI Pooling之后的ROI-wise子网络(用来对每个ROI进行特征提出,并进行回归和分类)。第1部分就是直接用普通分类网络的卷积层,用来提取共享特征,然后利用ROI Pooling在最后一层网络形成的feature map上面提取针对各个RoIs的特征向量,然后将所有RoIs的特征向量都交给第2部分来处理(即所谓的分类和回归),而第二部分一般都是一些全连接层,在最后有2个并行的loss函数:softmax和smoothL1,分别用来对每一个RoI进行分类和回归,这样就可以得到每个RoI的真实类别和较为精确的坐标信息啦(x, y, w, h)

 

RFCN 架构分析

r语言代谢物kegg富集_rfcn

  算法步骤:

     1.输入图片,第一部分子网(base network resnet101)进行特征提取,得到feature maps

     2.在预训练网络的最后一个卷积层获得的feature map上存在3个分支,第1个分支就是在该feature map上面进行RPN操作,获得相应的ROI;第2个分支就是在该feature map上获得一个K*K*(C+1)维的位置敏感得分映射(position-sensitive score map),用来进行分类;第3个分支就是在该feature map上获得一个4*K*K维的位置敏感得分映射,用来进行回归

     3.在K*K*(C+1)维的位置敏感得分映射和4*K*K维的位置敏感得分映射上面分别执行位置敏感的ROI池化操作(Position-Sensitive Rol Pooling,这里使用的是平均池化操作),获得对应的类别和位置信息。

position-sensitive score map

 

    

r语言代谢物kegg富集_position-sensitive_02

    如果一个RoI含有一个类别c的物体,那么作者将该RoI划分为

个区域,分别表示该物体的各个部位,比如假设该RoI中含有人这个物体,k=3,那么就将“人”划分为了9个子区域,top-center区域毫无疑问应该是人的头部,而bottom-center应该是人的脚部,而将RoI划分为

个区域是希望这个RoI在其中的每一个区域都应该含有该类别c的物体的各个部位,即如果是人,那么RoI的top-center区域就必须含有人的头部。而当这所有子区域都含有各自对应的该物体的相应部位后,那么分类器才会将该RoI判断为该类别。物体的各个部位和RoI的这些子区域是“一一映射”的对应关系。

 网络如何判断roi子区域是否含有物体的对应区域呢

 最后生成的(c+1)*k*k的矩阵,进行average pooling得到该roi属于c+1个类别的概率再做softmax得到最可能的类别

 Position-Sensitive Regression

前面的position-sensitive score map和Position-sensitive RoI pooling得到的值是用来分类的,那么自然需要相应的操作得到对应的值来进行回归操作。按照position-sensitive score map和Position-sensitive RoI pooling思路,其会让每一个RoI得到(C+1)个数作为每个类别的score,那么现在每个RoI还需要 4个数作为回归偏移量,也就是x,y,w,h的偏移量,所以仿照分类设计的思想,我们还需要一个类似于position-sensitive score map的用于回归的score map。

在ResNet的共享卷积层的最后一层上面连接一个与position-sensitive score map并行的score maps,该score maps用来进行regression操作,我们将其命名为regression score map,而该regression score map的维度应当是 4*K*K ,然后经过Position-sensitive RoI pooling操作后,每一个RoI就能得到4个值作为该RoI的x,y,w,h的偏移量了,其思路和分类完全相同。

网络训练

 为什么position-sensitive score map能够具有“在含有某个类别的物体的某个部位的区域上有高响应值”(网络训练要求达到的效果)

首先根据网络的loss公式,如果一个RoI含有人这个物体,那么该RoI通过“position-sensitive score map”+“Position-sensitive RoI pooling”得到的

个值中的属于人的那个值必然会在softmax损失函数的要求下“变得尽量的大”,那么如何才能使得属于人的这个值尽量的大呢?那么我们现在就要想到,属于人的这个预测值是怎么来的?在前面的分析,我们已经知道它是通过Position-sensitive RoI pooling这种池化操作的来的,那么也就是说使得

个值中属于人的那个值尽量大,必然会使得position-sensitive score map中属于人的那个score map上的“该RoI对应的位置区域的平均值”尽量大,从而也就是该score map上在该区域上的响应值尽量大,因为只有该区域的响应值大了,才能使得预测为人的概率大,才会降低softmax的loss。

  损失函数:

   

r语言代谢物kegg富集_rfcn_03

    对于任意一个RoI,计算它的softmax损失,和“当其不属于背景时的回归损失”。这很简单,因为每个RoI都被指定属于某一个GT box或者属于背景,即先让GT box选择与其IoU最大的那个RoI,然后再对剩余RoI选择与GT box的IoU>0.5的进行匹配,而剩下的RoI全部为背景类别。那么RoI有了label后,loss自然很容易计算出来。

 

在测试的时候,为了减少RoIs的数量,作者在RPN提取阶段就将RPN提取的大约2W个proposals进行过滤:

  1. 去除超过图像边界的proposals
  2. 使用基于类别概率且阈值IoU=0.7的NMS过滤
  3. 按照类别概率选择top-N个proposals

所以在测试的时候,一般只剩下300个RoIs,当然这个数量是一个超参数。并且在R-FCN的输出300个预测框之后,仍然要对其使用NMS去除冗余的预测框。

ROI是如何映射到feature map的(第四个参考)

RoI的坐标应该相对于原始image的真实坐标,而Position-sensitive RoI pooling的池化操作却是利用RoI在position-sensitive score map上完成的,那么现在就必须有一个映射关系将输入image上的RoI映射到position-sensitive score map上。

ROI Pooling :

 ROI pooling操作的输入(对于C+1个类)是k^2*(C+1)*W' *H'(W'和H'是ROI的宽度和高度)的score map上某ROI对应的那个立体块,且该立体块组成一个新的k^2*(C+1)*W' *H'的立体块:每个颜色的立体块(C+1)都只抠出对应位置的一个bin,把这k*k个bin组成新的立体块,大小为(C+1)*W'*H'。例如,下图中的第一块黄色只取左上角的bin,最后一块淡蓝色只取右下角的bin。所有的bin重新组合后就变成了类似右图的那个薄的立体块(图中的这个是池化后的输出,即每个面上的每个bin上已经是一个像素。池化前这个bin对应的是一个区域,是多个像素)。ROI pooling的输出为为一个(C+1)*k*k的立体块。

  

参考:

  https://www.jianshu.com/p/409fd61db9db

 https://zhuanlan.zhihu.com/p/30867916  https://zhuanlan.zhihu.com/p/24780433