天天看點

Faster Rcnn源碼閱讀之Roi_pooling 層

首先 RoI pooling 層的代碼位于model/roi_pooling 下

主要檔案為: functions/roi_pool.py

roi_pools 的初始化:

1,pooled_height pool之後feature map的高

2,pooled_width pool之後feature map的寬

3,spatial_scale feature map 原圖的大小比例

過程:

具體算法過程是在functions/roi_pooling.c(cup)/roi_pooling_cuda.c(gpn)中實作的

以下是前向傳播的代碼

将rois /spatial_scale,将rois的映射到feature map上,得到feature map上的bbox的坐标
//找到roi對應的圖檔在batch中的索引
        int roi_batch_ind = rois_flat[index_roi + 0];
        //得到roi在特征圖上的位置
        int roi_start_w = round(rois_flat[index_roi + 1] * spatial_scale);
        int roi_start_h = round(rois_flat[index_roi + 2] * spatial_scale);
        int roi_end_w = round(rois_flat[index_roi + 3] * spatial_scale);
        int roi_end_h = round(rois_flat[index_roi + 4] * spatial_scale);
        //      CHECK_GE(roi_batch_ind, 0);
        //      CHECK_LT(roi_batch_ind, batch_size);
     //得到roi在共享卷積層的高,寬
        int roi_height = fmaxf(roi_end_h - roi_start_h + 1, 1);
        int roi_width = fmaxf(roi_end_w - roi_start_w + 1, 1);
        //這個roi在pooling的時候會被分成多少段
        float bin_size_h = (float)(roi_height) / (float)(pooled_height);
        float bin_size_w = (float)(roi_width) / (float)(pooled_width);

2  //找max,在該區域中循環每一個點的值,找到最大的點,作為該區域pooling後對應點的值。
                                if (data_flat[index_data + index] > output_flat[pool_index + c * output_area])
                                {
                                    output_flat[pool_index + c * output_area] = data_flat[index_data + index];
                                }
           

看一下forward的輸入

1,feature maps:共享卷積層穿過來的特征

2,rois: rpn層選出來的框

輸出:固定大小 w*h的矩形框

前傳的代碼三個檔案都差不多的。

下面看下反向傳播

roi_pool.py 的反向傳播,主要調用了roi_pooling_cuda中的反向傳播

代碼。

//周遊該點對于特征圖上高的區域
        for (int ph = phstart; ph < phend; ++ph) {
             //周遊該點對于特征圖上寬的區域
            for (int pw = pwstart; pw < pwend; ++pw) {
                if (offset_argmax_data[(c * pooled_height + ph) * pooled_width + pw] == index)
                {

                //找到點,累計剃度
                    gradient += offset_top_diff[(c * pooled_height + ph) * pooled_width + pw];
                }
            }
        }
           

反向傳播中

輸入:grad_output剃度,在roi_pooling_cuda計算累加剃度用的。但是具體怎麼傳進來的,代表什麼意思。需要看上一層的代碼。

輸出:累加剃度

ok,roi 層就完成了。将rois映射到feature map上,然後劃分成固定大小

m * n的區域,每一個區域輸出最大值,輸出最後pool成固定的m*n的map。

繼續閱讀