最近在看image segmentation的論文,有篇題為《Hybrid Task Cascade For Instance Segmentation》的paper寫得非常地不錯,為了很好地理解該篇論文,我順便把其引用的幾篇重要論文以及對應的源碼(mmdetection),給看了。

這幾篇重要論文包括:

(1)Faster-RCNN:《Faster R-CNN: Towards Real-Time Object Detection with Region Proposal Networks》

(2)Mask-RCNN:《Mask R-CNN for Object Detection and Segmentation》

(3)Cascade-RCNN:《Cascade R-CNN: Delving into High Quality Object Detection》

(4)HTC:《Hybrid Task Cascade For Instance Segmentation》

首先介紹:Faster-RCNN

Faster-RCNN模型是目標檢測領域一篇很牛逼的論文,它提出了一種名為RPN(Region Proposal Network)的網路結構,來提出候選框(bounding box),並以此替代傳統方法(比如RCNN/Fast RCNN)中的Selective Search方法。解決了Fast RCNN演算法沒有實時性的問題。

這是Faster-RCNN的總體結構圖。具體來說,

輸入:被resize為w*h的圖

操作:(1)經過多層卷積操作,得到feature maps,(2)這個feature maps一方面輸出給RPN網路用於提取多個候選框,每個候選框的格式為(x,y,w,h);另一方面,feature maps與單個候選框結合,從feature map中唯一定位出局部圖像(image patch),多個候選框能得到多個局部圖像(image patch)。(3)由於每個局部圖像(image patch)的大小不一,將其輸入給ROI Pooling層,處理成相同大小的feature map。至此,每個得到長度相同的feature map;(4)將每個feature map分別輸入給classifier和bbox regression,得到這個局部圖像的分類,以及候選框的位置回歸。

輸出:目標物的候選框。具體:每個候選框都會有類別分數(來自classifier),以及候選框位置的精確調整值(來自bbox regression)。這裡根據類別分數,確定候選框屬於哪個目標類別;根據位置調整值,調整RPN輸出的位置: (x,y,w,h)
ightarrow(x^{},y^{},w^{},h^{})

Faster RCNN模型的結構總覽圖

具體介紹:

具體細節圖如下圖所示:

Faster RCNN的細節圖

操作(0):首先將不同大小的輸入圖像,resize為固定大小M*N的圖像

操作(1)是多個conv+relu+pooling的組合,這裡選擇有很多,比如VGG-Net,ResNet50,比如:ResNet50取stage2輸出的feature maps。這部分比較簡單,不再過多描述。

操作(2):RPN網路主要用於候選框的獲取。

def forward_single(self, x):
x = self.rpn_conv(x)
x = F.relu(x, inplace=True)
rpn_cls_score = self.rpn_cls(x)
rpn_bbox_pred = self.rpn_reg(x)
return rpn_cls_score, rpn_bbox_pred

其中,x為操作(1)輸出的feature maps,rpn_conv為一層3*3 的卷積操作,rpn_cls為1*1的卷積操作,out_channel = num_anchor * num_classes,比如 anchor_scales=[2, 4, 8], anchor_ratios=[0.5, 1.0, 2.0],那麼num_anchor=3*3=9,比如RPN階段只區分前景和後景,那麼num_classes=2,這裡out_channel=9*2=18。rpn_reg為1*1的卷積操作,out_channel=num_anchor * 4,4表示每個anchor都擁有(x,y,w,h)四個值,這裡out_channel=9*4=36。

rpn_cls_score = rpn_cls_score.reshape(-1, 2)
scores = rpn_cls_score.softmax(dim=1)[:, 1]

這裡對rpn_cls做reshape,是為了方便計算softmax值,每個bbox都會有兩個概率值:前景概率/後景概率,用於判定bbox中的圖像(image patch)是否屬於前景/後景。

# 取top_nms_pre
_, topk_inds = scores.topk(nms_pre)
rpn_bbox_pred = rpn_bbox_pred[topk_inds, :]
anchors = anchors[topk_inds, :]
scores = scores[topk_inds]
....
proposals, _ = nms(proposals, nms_thr)
proposals = proposals[nms_post, :]

然後根據前景值對scores進行排序,取前nms_pre個的scores值,以及其對應的rpn_bbox_pred和anchors。根據rpn_bbpx_pred對anchors的location進行微調,獲得調整後的bbox,(x,y,w,h)
ightarrow(x^{},y^{},w^{},h^{}) 。接著,做bbox的二次過濾,使用非極值抑製法(nms)過濾部分bbox,並取前nms_post個bbox(此時proposals是有序的)。最終輸出bbox。

需要說明的是,這裡的anchors的來源,每個像素點都會有num_anchor個anchor,那麼對於大小為w*h的feature map,就會有w*h*num_anchor個bbox。anchors是這bbox的集合,這裡可以根據像素點位置,以及anchor_scales和anchor_ratios唯一確定出bbox的位置(x,y,w,h)。後續的rpn_bbox_pred和rpn_cls都是對這w*h*num_anchor個bbox的位置回歸,以及給出類別分數。

anchor展示,這裡每個點都有3個anchor

操作(3)每個bbox都可以在feature map上唯一定位出一個局部圖像(image patch),它們大小不一,這裡使用ROI Pooing層對其進行統一, 得到統一大小的feature map。

操作(4):將feature map輸入給多層卷積,做特徵提取。然後一方面輸出給fc層,得到bbox_pred,另一方面輸出給fc層+softmax層,得到cls_prob。

圖像後處理階段:根據bbox_pred對rpn輸出的bbox的location進行微調,利用cls_prob來判定該bbox所在區域為哪個目標物。然後利用非極值抑制演算法過濾無效bbox,得到最終的輸出。

接著介紹Mask-RCNN

Mask-RCNN部分,介紹地特別地好,可以參考:zhuanlan.zhihu.com/p/37

接著介紹Cascade RCNN

未完,待續


推薦閱讀:
相關文章