参考博客:
1、https://blog.csdn.net/e01528/article/details/83618169
一、整体结构
二、RPN详解
1、通过VGG16网络模型提取Feature Map:
CNN:13个conv层,13个relu层,4个pooling层。这里有一个非常容易被忽略但是又无比重要的信息,在Conv layers中:
所有的conv层都是:kernel_size=3 , pad=1 ,stride=1
所有的pooling层都是:kernel_size=2 , pad=0 ,stride=2
最终一个MxN大小的矩阵经过Conv layers固定变为(M/16)x(N/16),本文中为38×63;
2、1×1全卷积层
首先是一个512×3×3的conv+relu;紧跟着一个18×1×1(cls),一个36×1×1(reg)的全连接功能层;
3、anchor_target_layer_>rpn_data
首先是cls;rpn_data层(anchor_target_layer类型的层);
输入:
bottom: 'rpn_cls_score' #[1,2*k,H,W] 类似与fc层的输出
bottom: 'gt_boxes'
bottom: 'im_info' #原图c h w,因为坐标回归的是原图坐标的xy偏移,需要用hw过滤不在图片内部的
bottom: 'data'
输出
K表示9个anchor,3*3,HW表示的是rpn第一层卷积的特征图的宽高。
top: 'rpn_labels' # [1,1,k*H,W] 生成rpn的标签,前景为1,背景为0,然后给softmaxLoss层
top: 'rpn_bbox_targets' #[1,4*K,H,W] smooth_l1_loss输入
top: 'rpn_bbox_inside_weights' #[1,4*K,H,W]smooth_l1_loss输入权重
top: 'rpn_bbox_outside_weights' #[1,4*K,H,W] smooth_l1_loss输入权重
将 20000 多个候选的 anchor 选出 256 个 anchor 进行分类和回归位置。选择过程如下:
- 对于每一个 ground truth bounding box (gt_bbox),选择和它重叠度(IoU)最高的一个 anchor 作为正样本
- 对于剩下的 anchor,从中选择和任意一个gt_bbox重叠度超过 0.7 的 anchor,作为正样本,正样本的数目不超过 128 个
- 随机选择和gt_bbox重叠度小于 0.3 的 anchor 作为负样本。负样本和正样本的总数为 256。例如:正样本100负样本156
对于每个 anchor, gt_label 要么为 1(前景),要么为 0(背景),而 gt_loc 则是由 4 个位置参数 (tx,ty,tw,th) 组成,这样比直接回归座标更好。
3、二分类Softmaxloss
求二分类的loss的时候,Softmaxloss,输入是rpn_lables(自己生成的rpn标签)+rpn_cls_scole_reshape;
4. 回归损失 rpn_loss_bbox
输入rpn_data 生成的rpn的bbox相关信息,与fc层rpn_bbox_pred(预测的)一起作为输入,进行损失计算。
两个输入的维度都是[1,4*k,H,W],不需要reshape操作。
5. softmax 二分类分类概率
输入[1,2,kH,W]:rpn_cls_scole_reshape(预测的)
输出[1,2,kH,W]:得到所有anchor的二分类的概率rpn_cls_prob。
6. prosal_layer_>2000个rpn_rois
首先需要softmax的结果,进行reshape[1,2,kH,W]_>[1,2k,H,W],这样与其他的输入是类似的。
输出: rpn_rois [1,5]
bottom: 'rpn_cls_prob_reshape' #[1,18,H,W]每个框经过softmax对应的概率
bottom: 'rpn_bbox_pred' #[1,36,H,W]预测的框运算loss,反向传播,越来越准
bottom: 'im_info'
top: 'rpn_rois' #[1,5]
- 对于每张图片,利用它的 feature map, 计算 (H/16)× (W/16)×9(大概 20000)个 anchor 属于前景的概率,以及对应的位置参数【softmax二分类概率】
- rpn_cls_prob_reshape始终连存储的是每个anchor 的偏移。
- 选取概率较大的 12000 个 anchor
- 利用回归的位置参数,修正这 12000 个 anchor 的位置,得到 rpn_rois
- 利用非极大值((Non-maximum suppression, NMS)抑制,选出概率最大的 2000 个 rpn_rois
7、proposal_target_layer_> roi_data 128 个RoIs
bottom: 'rpn_rois'[1,5]
bottom: 'gt_boxes'[1,4]
top: 'rois'[1,5,1,1]
top: 'labels'[1,1,1,1]
top: 'bbox_targets' #[1,8,1,1]存储的是anchors和最高重叠的gt的(x*-xa)/wa,(y*-ya)/ha,log(w*/wa),log(h*/hg),*为gt。
top: 'bbox_inside_weights' #[1,8,1,1]被抽中的正类为1,其他为0;
top: 'bbox_outside_weights #[1,8,1,1]外部权重,目前负例的外部权重=正例的外部权重=np.ones((1, 4)) * 1.0 /
RPN 会产生大约 2000 个 RoIs,这 2000 个 RoIs 不是都拿去训练,而是利用Proposal Target Creator 选择 128 个 RoIs 用以训练。选择的规则如下:
- rois 和 gt_bboxes 的 IoU 大于 0.5 的,选择一些(比如 32 个)
- 选择 RoIs 和 gt_bboxes 的 IoU 小于等于 0(或者 0.1)的选择一些(比如 128-32=96 个)作为负样本
- 为了便于训练,对选择出的 128 个 RoIs,还对他们的gt_roi_loc 进行标准化处理(减去均值除以标准差)
对于分类问题, 直接利用交叉熵损失. 而对于位置的回归损失, 一样采用 Smooth_L1_Loss, 只不过只对正样本计算损失. 而且是只对正样本中的这个类别 4 个参数计算损失。举例来说:
一个 RoI 在经过 FC 84 后会输出一个 84 维的 loc 向量. 如果这个 RoI 是负样本, 则这 84 维向量不参与计算 L1_Loss;如果这个 RoI 是正样本, 属于 label K, 那么它的第 K×4, K×4+1 ,K×4+2, K×4+3 这 4 个数参与计算损失,其余的不参与计算损失。