点击上方“小白学视觉”,选择加"星标"或“置顶

重磅干货,第一时间送达

池化操作(Pooling)是CNN中非常常见的一种操作,池化操作通常也叫做子采样(Subsampling)或降采样(Downsampling),在构建卷积神经网络时,往往会用在卷积层之后,通过池化来降低卷积层输出的特征维度,有效减少网络参数的同时还可以防止过拟合现象。

主要功能有以下几点:

  1. 抑制噪声,降低信息冗余

  2. 提升模型的尺度不变性、旋转不变形

  3. 降低模型计算量

  4. 防止过拟合

一提到池化操作,大部分人第一想到的就是maxpool和avgpool,实际上还有很多种池化操作。

大部分pooling操作满足上图的模型,假设输入大小为, 输出大小为, kernel size简称, stride简称,满足以下公式:

1. 最大/平均池化

最大池化就是选择图像区域中最大值作为该区域池化以后的值,反向传播的时候,梯度通过前向传播过程的最大值反向传播,其他位置梯度为0。

使用的时候,最大池化又分为重叠池化和非重叠池化,比如常见的stride=kernel size的情况属于非重叠池化,如果stride<kernel size 则属于重叠池化。重叠池化相比于非重叠池化不仅可以提升预测精度,同时在一定程度上可以缓解过拟合。

非重叠池化一个应用的例子就是yolov3-tiny的backbone最后一层,使用了一个stride=1, kernel size=2的maxpool进行特征的提取。

>>> import torch
>>> import torch.nn.functional as F
>>> input = torch.Tensor(4,3,16,16)
>>> output = F.max_pool2d(input, kernel_size=2, stride=2)
>>> output.shape
torch.Size([4, 3, 8, 8])
>>>

平均池化就是将选择的图像区域中的平均值作为该区域池化以后的值。

>>> import torch
>>> import torch.nn.functional as F
>>> input = torch.Tensor(4,3,16,16)
>>> output = F.avg_pool2d(input, kernel_size=2, stride=2)
>>> output.shape
torch.Size([4, 3, 8, 8])
>>>

2. 随机池化

Stochastic pooling如下图所示,特征区域的大小越大,代表其被选择的概率越高,比如左下角的本应该是选择7,但是由于引入概率,5也有一定几率被选中。

下表是随机池化在CIFAR-10上的表现,可以看出,使用随机池化效果和采用dropout的结果接近,证明了其有一定防止过拟合的作用。

更详细内容请看论文:《Stochastic Pooling for Regularization of Deep Convolutional Neural Networks》

3. 中值池化

与中值滤波特别相似,但是用的非常少,中值池化也具有学习边缘和纹理结构的特性,抗噪声能力比较强。

4. 组合池化

组合池化则是同时利用最大值池化与均值池化两种的优势而引申的一种池化策略。常见组合策略有两种:Cat与Add。常常被当做分类任务的一个trick,其作用就是丰富特征层,maxpool更关注重要的局部特征,而average pooling更关注全局特征。

def add_avgmax_pool2d(x, output_size=1):x_avg = F.adaptive_avg_pool2d(x, output_size)x_max = F.adaptive_max_pool2d(x, output_size)return 0.5 * (x_avg + x_max)def cat_avgmax_pool2d(x, output_size=1):x_avg = F.adaptive_avg_pool2d(x, output_size)x_max = F.adaptive_max_pool2d(x, output_size)return torch.cat([x_avg, x_max], 1)

5. Spatial Pyramid Pooling

SPP是在SPPNet中提出的,SPPNet提出比较早,在RCNN之后提出的,用于解决重复卷积计算和固定输出的两个问题,具体方法如下图所示:

在feature map上通过selective search获得窗口,然后将这些区域输入到CNN中,然后进行分类。

实际上SPP就是多个空间池化的组合,对不同输出尺度采用不同的划窗大小和步长以确保输出尺度相同,同时能够融合金字塔提取出的多种尺度特征,能够提取更丰富的语义信息。常用于多尺度训练和目标检测中的RPN网络。

在YOLOv3中有一个网络结构叫yolov3-spp.cfg, 这个网络往往能达到比yolov3.cfg本身更高的准确率,具体cfg如下:

### SPP ###
[maxpool]
stride=1
size=5[route]
layers=-2[maxpool]
stride=1
size=9[route]
layers=-4[maxpool]
stride=1
size=13[route]
layers=-1,-3,-5,-6### End SPP ###

这里的SPP相当于是原来的SPPNet的变体,通过使用多个kernel size的maxpool,最终将所有feature map进行concate,得到新的特征组合。

再来看一下官方提供的yolov3和yolov3-spp在COCO数据集上的对比:

可以看到,在几乎不增加FLOPS的情况下,YOLOv3-SPP要比YOLOv3-608mAP高接近3个百分点。

分析一下SPP有效的原因:

  1. 从感受野角度来讲,之前计算感受野的时候可以明显发现,maxpool的操作对感受野的影响非常大,其中主要取决于kernel size大小。在SPP中,使用了kernel size非常大的maxpool会极大提高模型的感受野,笔者没有详细计算过darknet53这个backbone的感受野,在COCO上有效很可能是因为backbone的感受野还不够大。

  2. 第二个角度是从Attention的角度考虑,这一点启发自CSDN@小楞(链接在参考文献中),他在文章中这样讲:

出现检测效果提升的原因:通过spp模块实现局部特征和全局特征(所以空间金字塔池化结构的最大的池化核要尽可能的接近等于需要池化的featherMap的大小)的featherMap级别的融合,丰富最终特征图的表达能力,从而提高MAP。

Attention机制很多都是为了解决远距离依赖问题,通过使用kernel size接近特征图的size可以以比较小的计算代价解决这个问题。另外就是如果使用了SPP模块,就没有必要在SPP后继续使用其他空间注意力模块比如SK block,因为他们作用相似,可能会有一定冗余。

ps: 这个想法还没有进行试验的验证,有兴趣的可以将YOLOv3-spp中的kernel size改为19,然后在COCO数据集上测试,看是否能够超越60.6。

6. Global Average/Max Pooling

Gloabel Average Pooling 是NIN里边的做法,一般使用torchvision提供的预训练模型进行finetune的时候,通常使用Global Average Pooling,原因就是可以不考虑图片的输入尺寸,只与filter有关。

>>> import torch
>>> from torch.nn import AdaptiveAvgPool2d
>>> input = torch.zeros((4,12,18,18)) # batch size, fileter, h, w
>>> gap = AdaptiveAvgPool2d(1)
>>> output = gap(input)
>>> output.shape
torch.Size([4, 12, 1, 1])
>>> output.view(input.shape[0],-1).shape
torch.Size([4, 12])
>>>

7. NetVLAD池化

这部分来自:DeepLearning-500-questions#5

NetVLAD是论文《NetVLAD: CNN Architecture for Weakly Supervised Place Recognition》提出的一个局部特征聚合的方法。

在传统的网络里面,例如VGG啊,最后一层卷积层输出的特征都是类似于Batchsize x 3 x 3 x 512的这种东西,然后会经过FC聚合,或者进行一个Global Average Pooling(NIN里的做法),或者怎么样,变成一个向量型的特征,然后进行Softmax or 其他的Loss。

这种方法说简单点也就是输入一个图片或者什么的结构性数据,然后经过特征提取得到一个长度固定的向量,之后可以用度量的方法去进行后续的操作,比如分类啊,检索啊,相似度对比等等。

那么NetVLAD考虑的主要是最后一层卷积层输出的特征这里,我们不想直接进行欠采样或者全局映射得到特征,对于最后一层输出的W x H x D,设计一个新的池化,去聚合一个“局部特征“,这即是NetVLAD的作用。

NetVLAD的一个输入是一个W x H x D的图像特征,例如VGG-Net最后的3 x 3 x 512这样的矩阵,在网络中还需加一个维度为Batchsize。

NetVLAD还需要另输入一个标量K即表示VLAD的聚类中心数量,它主要是来构成一个矩阵C,是通过原数据算出来的每一个特征的聚类中心,C的shape即,然后根据三个输入,VLAD是计算下式的V:

402 Payment Required

其中j表示维度,从1到D,可以看到V的j是和输入与c对应的,对每个类别k,都对所有的x进行了计算,如果属于当前类别k,,否则,计算每一个x和它聚类中心的残差,然后把残差加起来,即是每个类别k的结果,最后分别L2正则后拉成一个长向量后再做L2正则,正则非常的重要,因为这样才能统一所有聚类算出来的值,而残差和的目的主要是消减不同聚类上的分布不均,两者共同作用才能得到最后正常的输出。

输入与输出如下图所示:

NETVALD示意图

中间得到的K个D维向量即是对D个x都进行了与聚类中心计算残差和的过程,最终把K个D维向量合起来后进行即得到最终输出的长度的一维向量。

而VLAD本身是不可微的,因为上面的a要么是0要么是1,表示要么当前描述x是当前聚类,要么不是,是个离散的,NetVLAD为了能够在深度卷积网络里使用反向传播进行训练,对a进行了修正。

那么问题就是如何重构一个a,使其能够评估当前的这个x和各个聚类的关联程度?用softmax来得到:

402 Payment Required

将这个把上面的a替换后,即是NetVLAD的公式,可以进行反向传播更新参数。

所以一共有三个可训练参数,上式a中的,上式a中的,聚类中心,而原始VLAD只有一个参数c。

最终池化得到的输出是一个恒定的K x D的一维向量(经过了L2正则),如果带Batchsize,输出即为Batchsize x (K x D)的二维矩阵。

NetVLAD作为池化层嵌入CNN网络即如下图所示,

image

原论文中采用将传统图像检索方法VLAD进行改进后应用在CNN的池化部分作为一种另类的局部特征池化,在场景检索上取得了很好的效果。

后续相继又提出了ActionVLAD、ghostVLAD等改进。

评价:这个NetVLAD Layer和SENet非常相似,可以看做是通道注意力机制的实现,不过具体实现方法有别于SENet。

8. 双线性池化

Bilinear Pooling是在《Bilinear CNN Models for Fine-grained Visual Recognition》被提出的,主要用在细粒度分类网络中。双线性池化主要用于特征融合,对于同一个样本提取得到的特征x和特征y, 通过双线性池化来融合两个特征(外积),进而提高模型分类的能力。

主要思想是对于两个不同图像特征的处理方式上的不同。传统的,对于图像的不同特征,我们常用的方法是进行串联(连接),或者进行sum,或者max-pooling。论文的主要思想是,研究发现人类的大脑发现,人类的视觉处理主要有两个pathway, the ventral stream是进行物体识别的,the dorsal stream 是为了发现物体的位置。

论文基于这样的思想,希望能够将两个不同特征进行结合来共同发挥作用,提高细粒度图像的分类效果。论文希望两个特征能分别表示图像的位置和对图形进行识别。论文提出了一种Bilinear Model。

如果特征 x 和特征y来自两个特征提取器,则被称为多模双线性池化(MBP,Multimodal Bilinear Pooling)

如果特征 x = 特征 y,则被称为同源双线性池化(HBP,Homogeneous Bilinear Pooling)或者二阶池化(Second-order Pooling)。

pytorch实现:

X = torch.reshape(N, D, H * W)                        # Assume X has shape N*D*H*W
X = torch.bmm(X, torch.transpose(X, 1, 2)) / (H * W)  # Bilinear pooling
assert X.size() == (N, D, D)
X = torch.reshape(X, (N, D * D))
X = torch.sign(X) * torch.sqrt(torch.abs(X) + 1e-5)   # Signed-sqrt normalization
X = torch.nn.functional.normalize(X)                  # L2 normalization

之后又有很多人出于对双线性池化存在的特征维度过高等问题进行各种改进,具体可以看知乎文章:

https://zhuanlan.zhihu.com/p/62532887

9. UnPooling

是一种上采样操作,具体操作如下:

流程描述:

1.在Pooling(一般是Max Pooling)时,保存最大值的位置。

2.中间经历若干网络层的运算。

3.上采样阶段,利用第1步保存的Max Location,重建下一层的feature map。

UnPooling不完全是Pooling的逆运算,Pooling之后的feature map,要经过若干运算,才会进行UnPooling操作;对于非Max Location的地方以零填充。然而这样并不能完全还原信息。

好消息! 

小白学视觉知识星球

开始面向外开放啦

【综述】盘点卷积神经网络中的池化操作相关推荐

  1. 卷积神经网络中的池化是什么意思

    卷积神经网络中的池化是什么意思 pooling 理论在于,图像中相邻位置的像素是相关的.对一幅图像每隔一行采样,得到的结果依然能看. 经过一层卷积以后,输入的图像尺寸变化不大,只是缩小了卷积核-1.根 ...

  2. 卷积神经网络中的池化(Pooling)层

    文章目录 卷积神经网络中的池化(Pooling)层 ⚪ 通用的池化方法 1. 最大池化 Max Pooling 2. 平均池化 Average Pooling 3. 混合池化 Mix Pooling ...

  3. 【TensorFlow】TensorFlow从浅入深系列之十二 -- 教你深入理解卷积神经网络中的池化层

    本文是<TensorFlow从浅入深>系列之第12篇 TensorFlow从浅入深系列之一 -- 教你如何设置学习率(指数衰减法) TensorFlow从浅入深系列之二 -- 教你通过思维 ...

  4. 卷积神经网络中的池化方法(pooling)总结

    在卷积神经网络中,我们经常会碰到池化操作,而池化层往往在卷积层后面,通过池化来降低卷积层输出的特征向量,同时改善结果(不易出现过拟合). 为什么可以通过降低维度呢? 因为图像具有一种"静态性 ...

  5. 【CMU】图卷积神经网络中的池化综述,Pooling in Graph Convolutional Neural Network

    关注上方"深度学习技术前沿",选择"星标公众号", 资源干货,第一时间送达! 图卷积神经网络(GCNNs)是深度学习技术在图结构数据问题上的一种强大的扩展.我们 ...

  6. 花书+吴恩达深度学习(十一)卷积神经网络 CNN 之池化层

    目录 0. 前言 1. 最大池化(max pooling) 2. 平移不变形 3. 其他池化函数 4. 卷积和池化作为一种无限强的先验 如果这篇文章对你有一点小小的帮助,请给个关注,点个赞喔~我会非常 ...

  7. 深度学习(一)神经网络中的池化与反池化原理

    原文作者:aircraft 原文链接:https://www.cnblogs.com/DOMLX/p/9579108.html 参考博客:https://blog.csdn.net/chengqium ...

  8. 盘点卷积神经网络中十大令人拍案叫绝的操作

    转载自https://www.jianshu.com/p/71804c97123d CNN从2012年的AlexNet发展至今,科学家们发明出各种各样的CNN模型,一个比一个深,一个比一个准确,一个比 ...

  9. 机器学习入门(18)— 卷积网络中的池化层实现

    1. 池化层实现 池化层的实现和卷积层相同,都使用 im2col 展开输入数据.不过,池化的情况下,在通道方向上是独立的,这一点和卷积层不同.具体地讲,如图 7-21 所示,池化的应用区域按通道单独展 ...

最新文章

  1. 《python 与数据挖掘 》一1.3 Python开发环境的搭建
  2. 远程代理模式-Remote Proxy(Java实现)
  3. C++ Primer 5th笔记(chap 13 拷贝控制)综述
  4. WEB页面多语言支持解决方案(转自CSDN)
  5. JavaScript---Ajax和函数回调,异步编程
  6. 逍遥自动秒收录导航网源码绿色版+全站SEO优化
  7. 7-46 最长对称子串 (25 分)
  8. 计算机考试忘记备注班级了,2012年计算机二级Access第二十五套上机试题及答案详解...
  9. URLDecoder.decode()转义处理
  10. 面试整理—计算机及网络工程师常见问题
  11. Spring Boot入门教程(零): yaml使用详解
  12. 浏览器 实现复制粘贴 上传图片, js实现粘贴图片预览功能
  13. 关于图片的Exif信息
  14. SSM搭建-Spring第一个Spring HelloWorld(2)
  15. MyBatis在字段返回为null不返回字段
  16. 常用邮箱POP,SMTP服务器列表
  17. Oracle同义词总结
  18. 使用Python+selenium实例化Microsoft Edge或Chrome浏览器对象和常见的报错
  19. AnyDesk 未连接到服务器。请检查您的互联网连接
  20. 解决Grails2.0-M1下 Intellij IDEA 中Controller等无法自动重新加载的BUG

热门文章

  1. VOGUE: Secure User Voice Authentication on Wearable Devices using Gyroscope
  2. Android微信h5分享,H5网页实现微信分享功能
  3. 一个UI设计师在工作中所需要具备的综合能力!
  4. Go实战--也许最快的Go语言Web框架kataras/iris初识(basic认证、Markdown、YAML、Json)
  5. python的安装和配置环境变量
  6. 华为IOT,技术干货
  7. 二分法求方程根matlab,matlab用二分法求方程 的正根,要求误差小于0.0005
  8. 背靠巨头阿里的淘菜菜,能在社区团购赛道走多远?
  9. 不同的AI视频推理场景下,如何构建通用高效的抽帧工具?
  10. 站群优化关键词-站群优化工具软件免费