这篇文章的主要目的是通过分析mmdetection的源码,读懂faster-rcnn的同时,也能更加深刻的理解mmdetection的代码,方便以后的模型修改和自己实现各种算法。在读文章之前尽量对mmdetection有一定了解,并且能够跑通代码。
这里主要介绍模型构建相关的几个模块以及如何拼接到一起的:
1.backbone
2.neck
3.rpn_head
4.bbox_roi_extractor
5.bbox_head
源码分析:
1.Faster-RCNN整体流程分析
这里以输入大小为(800,800), batch_size=2为例
def
2.1 Backbone
这里对于backbone的设置信息如下
backbone
请先注意resnet的网络结构
depth 指使用resnet50 对应图上(3,4,6,3)
num_stages=4 对应的是C2、C3、C4、C5这四层
out_indices=(0, 1, 2, 3) 指输出哪几层卷积后的特征作为输出,0-C2,1-C3,2-C4,3-C5,
def
经过self.backbone(img)后,会返回结构为: tuple(tensor(2,256,200,200), tensor(2,256,100,100), tensor(2,256,50,50), tensor(2,256,25,25)) C2、C3、C4、C5四层对应的featuremap特征x
resnet的详细实现代码很简单,相信大家对照着论文+代码都能理解。
2.2 FPN
紧接着,将x输入到neck中,也就是fpn结构中,我这里fpn的设置参数为
neck
这里简单的画出fpn的实现逻辑
上图是mm中的fpn的基本流程,生成P6层是因为num_outs=5,所以会在P5层,通过maxpool或者conv进行降采样特征提取,生成P6
def
2.3 rpn_head
2.3.1 rpn阶段主要是为了提取proposal候选框,rpn的配置如下
rpn_head
先简单介绍一下mm中候选框的生成,featuremap的每个点映射会原图生成的anchor个数anchor_base=num(anchor_scales)*num(anchorratios), 这里anchor_base=3
anchorstrides对应P2-P6五层,代表将采样的步长,结合fpn生成anchor的方式是:比如P2层生成anchor_size=200*200*anchor_base, P3-P6同理
anchor_base的详细生成过程,可以看我的另一篇文章。
rpn的前向传播
def
2.3.2 前向传播之后,计算rpn的loss
def
2.3.3 rpn的loss计算完成后,通过getbboxes获取前2000个分值最高的proposal作为rcnn输入,mmdet.models.anchor_heads下的rpn_head.py和anchor_head.py文件中get_bboxes和get_bboxes_single函数,这里介绍get_bboxes_single,对应得配置文件
rpn_proposal
代码解析
def
2.3.4 获取到proposals 后,继续通过配置文件中的rcnn配置,对proposals进行assigner和sampler操作 ;
我这里rcnn中使用的配置是
rcnn
MaxIoUAssigner中的assigner操作
def
RandomSampler中的sampler操作比较简单,从AssignResult中结果中随机选取512个,25%的正例,75%的负例,正例不足时用负例补齐。
2.4 bbox_roi_extractor
roi_align里面的featuremap是个参照,双线新插值的是那512个proposals,proposals的大小是相对原图的,要把它先映射到对应的featuremap大小里面,然后在对proposal做双线性插值
配置信息
bbox_roi_extractor
代码解读
def
2.5 bbox_head
这个阶段就是对roi操作之后的proposals进行后续的卷积、全连接、以及预测了
配置信息
bbox_head
代码解读,没有太多讲的,就是一些卷积、全连接、预测结果的操作
def
本文主要是对mmdetection中的faster-rcnn的流程梳理了一遍,也同时方便自己记忆,有理解错误之处,请指出,一起探讨。