1. 为什么会提出ROI Pooling?
在Rcnn系列检测器中,rcnn在selective search后得到一系列的预选框,再将这些预选框 resize到同样大小的尺寸,通过卷积网络,再进行检测,这是因为固定的卷积网络需要同样大小的输入,这样多次通过网络,不仅费时,box之间存在大量的重复区域,也浪费了计算资源。
在之后改进的Faster rcnn中,图像通过卷积网络后得到feature map,此时根据预选框的位置坐标在对应到特征图中。但是每个预选框大小不同,对应在特征图的大小也不同。所以通过RO Pooling将特征图区域池化为固定尺寸,以便进行后续的分类和包围框回归操作
2. 为什么会提出ROI Align
由于预选框的位置通常是由模型回归得到的,一般来讲是浮点数,而池化后的特征图要求尺寸固定。故ROI Pooling这一操作存在两次量化的过程。
- 将候选框边界量化为整数点坐标值。
- 将量化后的边界区域平均分割成 k x k 个单元(bin),对每一个单元的边界进行量化。
从图中可以看到两次量化舍弃了小数位,第二次量化舍弃了小数点后的0.8,feature map尺寸是原图的1/32,所以一个像素的误差放大到原图就是接近32个像素。
所以需要一种可以尽量避免这种误差的替代方法
3. 方法本质
ROI Pooling的本质是最近邻插值法,即选取离点最近的像素点的值作为该点的值。
ROI Align的本质是双线性插值,即两个变量的插值函数的线性插值扩展,其核心思想是在两个方向分别进行一次线性插值。其原理是待插点像素值取原图像中与其相邻的4个点像素值的水平、垂直两个方向上的线性内插,即根据待采样点与周围4个邻点的++距离++确定相应的权重,从而计算出待采样点的像素值。
4.代码
mxnet里有定义好的函数,可以直接调用
from mxnet.ndarray import ROIPooling
from mxnet.contrib.ndarray import ROIAlign
x = mx.nd.array(
[[[[ 0., 1., 2., 3., 4., 5.],
[ 6., 7., 8., 9., 10., 11.],
[ 12., 13., 14., 15., 16., 17.],
[ 18., 19., 20., 21., 22., 23.],
[ 24., 25., 26., 27., 28., 29.],
[ 30., 31., 32., 33., 34., 35.],
[ 36., 37., 38., 39., 40., 41.],
[ 42., 43., 44., 45., 46., 47.]]]])
#// region of interest i.e. bounding box coordinates.
y = mx.nd.array([[0,0,0,3,3]])
#// returns array of shape (2,2) according to the given roi with max pooling.
print(ROIPooling(x, y, (2,2), 1.0))
[[[[ 7. 9.]
[19. 21.]]]]
<NDArray 1x1x2x2 @cpu(0)>
print(ROIAlign(x, y, (2,2), 1))
[[[[ 5.25 6.75]
[14.25 15.75]]]]
来源:CSDN
作者:再困也得吃
链接:https://blog.csdn.net/weixin_38208912/article/details/103915443