在http://www.cnblogs.com/jianyingzhou/p/4086578.html中
提到
rcnn開創性工作,但是計算時間太長,重復計算太大。
spp_net將重復計算避免了
我自己測試發現rcnn的確非常慢,因為窗口重疊,重復計算普遍
一下轉自 http://zhangliliang.com/2014/09/13/paper-note-sppnet/
對應的論文是:http://arxiv.org/pdf/1406.4729v2.pdf
對應的slide:http://research.microsoft.com/en-us/um/people/kahe/eccv14sppnet/sppnet_ilsvrc2014.pdf
作者Kaiming He的主頁:http://research.microsoft.com/en-us/um/people/kahe/
思路概述
如下圖所示,由於傳統的CNN限制了輸入必須固定大小(比如AlexNet是224x224),所以在實際使用中往往需要對原圖片進行crop或者warp的操作
- crop:截取原圖片的一個固定大小的patch
- warp:將原圖片的ROI縮放到一個固定大小的patch
無論是crop還是warp,都無法保證在不失真的情況下將圖片傳入到CNN當中。
- crop:物體可能會產生截斷,尤其是長寬比大的圖片。
- warp:物體被拉伸,失去“原形”,尤其是長寬比大的圖片
Sptial Pyramid Pooling,以下簡稱SPP,為的就是解決上述的問題,做到的效果為:不管輸入的圖片是什么尺度,都能夠正確的傳入網絡。
思路很直觀,首先發現了,CNN的卷積層是可以處理任意尺度的輸入的,只是在全連接層處有限制尺度——換句話說,如果找到一個方法,在全連接層之前將其輸入限制到等長,那么就解決了這個問題。
然后解決問題的方法就是SPP了。
從BoW到SPM
SPP的思想來源於SPM,然后SPM的思想來源自BoW。
關於BoW和SPM,找到了兩篇相關的博文,就不在這里展開了。
最后做到的效果如下圖:
如果原圖輸入是224x224,對於conv5出來后的輸出,是13x13x256的,可以理解成有256個這樣的filter,每個filter對應一張13x13的reponse map。
如果像上圖那樣將reponse map分成4x4 2x2 1x1三張子圖,做max pooling后,出來的特征就是固定長度的(16+4+1)x256那么多的維度了。
如果原圖的輸入不是224x224,出來的特征依然是(16+4+1)x256
直覺地說,可以理解成將原來固定大小為(3x3)窗口的pool5改成了自適應窗口大小,窗口的大小和reponse map成比例,保證了經過pooling后出來的feature的長度是一致的
如何訓練網絡
理論上說,SPP-net支持直接以多尺度的原始圖片作為輸入后直接BP即可。實際上,caffe等實現中,為了計算的方便,輸入是固定了尺度了的。
所以為了使得在固定輸出尺度的情況下也能夠做到SPP-net的效果,就需要定義一個新的SSP-layer
作者以輸入224x224舉例,這時候conv5出來的reponse map為13x13,計算出來的步長如下圖所示。
具體的計算方法,看一眼2.3的Single-size training部分就明白了。
如果輸入改成180x180,這時候conv5出來的reponse map為10x10,類似的方法,能夠得到新的pooling參數。
兩種尺度下,在SSP后,輸出的特征維度都是(9+4+1)x256,之后接全連接層即可。
訓練的時候,224x224的圖片通過隨機crop得到,180x180的圖片通過縮放224x224的圖片得到。之后,迭代訓練,即用224的圖片訓練一個epoch,之后180的圖片訓練一個epoth,交替地進行。
如何測試網絡
作者說了一句話:Note that the above single/multi-size solutions are for training only. At the testing stage, it is straightforward to apply SPP-net on images of any sizes.
筆者覺得沒有那么簡單吧,畢竟caffe對於test網絡也是有固定尺度的要求的。
實驗
之后是大量的實驗。
分類實驗
- 為了保證公平,test時候的做法是將圖片縮放到短邊為256,然后取10crop。這里的金字塔為{6x6 3x3 2x2 1x1}(筆者注意到,這里算是增加了特征,因為常規pool5后來說,只有6x6;這里另外多了9+4+1個特征)
- 作者將金字塔減少為{4x4 3x3 2x2 1x1},這樣子,每個filter的feature從原來的36減少為30,但依然有提高。(筆者認為這個還是保留意見比較好)
- 其實這部分的實驗比較多,詳見論文,不在這里寫了。
- 在ILSVRC14上的cls track,作者是第三名
定位實驗
這里詳細說說筆者較為關心的voc07上面的定位實驗
用來對比的對象是RCNN。
方法簡述:
- 提取region proposal部分依然用的是selective search
- CNN部分,結構用的是ZF-5(單尺度訓練),金字塔用了{6x6 3x3 2x2 1x1},共50個bin
- 分類器也是用了SVM,后處理也是用了cls-specific regression
所以主要差別是在第二步,做出的主要改進在於SPP-net能夠一次得到整個feature map,大大減少了計算proposal的特征時候的運算開銷。
具體做法,將圖片縮放到s∈{480,576,688,864,1200}的大小,於是得到了6個feature map。盡量讓region在s集合中對應的尺度接近224x224,然后選擇對應的feature map進行提取。(具體如何提取?后面的附錄會說)
最后效果如圖:
准確率從58.5提高到了59.2,而且速度快了24x
如果用兩個模型綜合,又提高了一點,到60.9
附錄
如何將圖像的ROI映射到feature map?
說實話,筆者還是沒有完全弄懂這里的操作。先記錄目前能夠理解的部分。
總體的映射思路為:In our implementation, we project the corner point of a window onto a pixel in the feature maps, such that this corner point (in the image
domain) is closest to the center of the receptive field of that pixel.
略繞,我的理解是:
- 映射的是ROI的兩個角點,左上角和右下角,這兩個角點就可以唯一確定ROI的位置了。
- 將feature map的pixel映射回來圖片空間
- 從映射回來的pixel中選擇一個距離角點最近的pixel,作為映射。
這里有幾個變量
- 139代表的是感受野的直徑,計算這個也需要一點技巧了:如果一個filter的kernelsize=x,stride=y,而輸出的reponse map的長度是n,那么其對應的感受野的長度為:n+(n-1)*(stride-1)+2*((kernelsize-1)/2)
- 16是effective stride,這里筆者理解為,將conv5的pixel映射到圖片空間后,兩個pixel之間的stride。(計算方法,所有stride連乘,對於ZF-5為2x2x2x2=16)
- 63和75怎么計算,還沒有推出來。。。。囧
寫的非常好,忍不住就轉了