前面个讲过了MobileNet系列,从V1到V3做了很多改进,效果也是越来越好。但是这些改进很多都是基于block来进行改进的,而这一问题就可以让我们直接将这个block用于其他backbone上面,并有着优秀的性能。在今年年初读到的这篇文章,当时就觉得很不错,也是仔细刨析了一下现在卷积和transformer的较量,给了我们坚定卷积的决心。在这篇文章中也是涉及到了前面中block中的一些改变。不过这些改变不是为了轻量型而做出的,在这里也是总结一下。感兴趣的小伙伴也可以看一下我前面这篇文章:MobileNet系列(万文长字详细讲解,一篇足以)。
ConvNets在整个计算机视觉领域的支配性不是巧合:在很多的应用实例中,滑动窗口策略是视觉处理的内在本质,尤其是处理高分辨率图像。ConvNets有一些内在的归纳偏置,使得他们能够很好适应多种计算机视觉应用。其中最重要的一个就是平移不变性,对于一些任务比如对象检测来说,它是令人满意的一个属性。ConvNets还有其高效率的特性,源于使用滑动窗口的方式使得其计算可共享。几十年来,通常在有限的对象分类方面,这些都成了ConvNets的默认的应用,比如手写字体识别、人脸检测、行人检测等。进入2010s之后,基于区域范围的对象检测进一步将ConvNets提升到了在视觉识别系统中基础模块的位置
But对于transformer来说,ViT的一个主要焦点是放大行为:有大模型和大量数据集的加持,其性能超出标准ResNet一个显著的差额(就是高出ResNet一大截!)。这些结果在图像分类任务上是令人鼓舞的,但计算机视觉不是只有图像分类任务。如前所述,过去十年相当数量的计算机视觉任务的解决方案很大程度上依赖于一个滑动窗口——全卷积范式。没有卷积网络的归纳偏置,一个(普通的)ViT模型要被采用作为视觉主干网络将面临诸多挑战。最大的挑战就是ViT的全局注意力机制的设计,它的计算复杂度是对应输入大小的二次方,在在ImageNet分类上还可以被接受,但难以实施在高分辨率图像的输入上。
分级Transformer采用混合方法来弥补这个差距。例如,重新引入滑动窗口策略(局部注意力机制),使他们能够表现的和ConvNets一样。SwinTransformer在这个方向上是一件里程碑式的工作,首次演示了Transformer可以被采用作为通用主干网络,并且在除了图像分类任务之外的范围内其性能取得了领先水平。SwinTransformer的成功和快速被采纳揭示了一件事情,卷积的本质并不是变得不相关,而是保持着更被需要且从未褪色。
在这个角度下,很多对计算机视觉的Transformers的改进都致力于回归卷积层面上。然而这些尝试需要付出一些代价:一个滑动窗口方式的自注意力机制的简单实现都是很昂贵的;有一些改进方法比如cyclic shifting(循环移位,说的就是SwinTransformer),虽然速度能被优化但是在设计上系统变得更复杂了。另一方面,具有讽刺意味的是,ConvNets本来已经满足这些期望的属性,尽管它是一种直白的、朴实的方法。ConvNets失势的唯一理由是(分层的)Transformer的性能超过了它们,并且性能的差异归功于Transformer的超强的缩放行为,因其加持了关键组件MSA(多头自注意力机制)。
综上原因,作者又对卷积进行了重新实验,测试一个纯卷积网络所能取得的性能极限。改进的过程从标准ResNet开始训练,也是对最小的block进行改变的实验。
在这个魔改之中总有一条主线,就是尽可能地将ResNet改成和Transformer相似的ConvNet。主要分为下面五个方面:
1)宏观设计
2)ResNeXt
3)反转瓶颈
4)大尺寸卷积核
5)各种层级别的微观设计
除了网络架构的设计之外,训练过程同样影响这最终性能。vision Transformer不仅带来一些新的模块集合以及架构设计决策,他们同样引入了不同的训练技巧,主要涉及优化策略和相关的超参数设置。因此,我们研究的第一步就是用vision Transformer的训练过程来训练baseline模型,就是ResNet50和ResNet200。作者使用了与Deit和SwinTransformer相似的训练诀窍:
1.从90个epoch扩大到300个epoch;
2.使用AdamW优化器(优化器详见我这篇文章);
3.数据增广:Mixup, Cutmix , RandAugment, Random Erasing;
4.正则化方案:Stochastic Depth, Label Smoothing;
所使用的的超参数见论文Appendix A.1,ResNet50从76.1提高到78.8,说明Transformer提升的性能主要还应归因于训练技巧。后续的魔改过程中,作者对所有模型采用固定的参数设置,所有获得的结果都是三个不同随机种子下训练结果的平均。
SwinTransformer沿袭着ConvNets的多阶段设计特点,每个阶段有不同的特征映射分辨率。这里有两个有趣的设计注意事项:阶段计算比、“干细胞”结构。
Changing stage compute ratio.ResNet中跨阶段的计算分布最初的设计很大程度上是基于经验的。res4阶段设计的重(块数多)是为了与下游的任务兼容,比如对象检测,在 14*14 特征平面上有一个探测头。另一方面,Swin-T遵循相同的原理,但阶段计算比例略有不同,为1:1:3:1。对于更大的Swin变形金刚,比例是1:1:9:1。按照这种设计,作者将每个阶段的块数从ResNet-50中的(3,4,6,3)调整为(3,3,9,3),这也将FLOPs与Swin-T对齐。这将模型的精度从78.8%提高到79.4%。值得注意的是,研究人员已经对计算的分布进行了深入的研究,可能存在更优化的设计。从现在开始,我们将使用这个阶段计算比率。
Changing stem to “Patchify”.通常,干细胞的设计是考虑在网络开始时如何处理输入的图像。由于自然图像固有的冗余性,在ConvNets和vision transformer中,普通干细胞会积极地将输入图像采样到合适的特征图大小。在标准ResNet中,干细胞包含一个 7*7 卷积层,stride 2,然后是一个最大池化,再4倍向下采样输出结果。在vision transformer中,使用了一种更激进的补丁化策略作为干细胞,它对应于较大的核大小(例如核大小= 14或16)和非重叠卷积。Swin Transformer使用了类似的补丁层,但补丁的大小更小,为4,以适应该架构的多阶段设计。作者将resnet类型的干细胞替换为一个补丁层,该补丁层使用 ,stride=4的卷积层实现。准确率从79.4%提高到79.5%。这表明ResNet中的干细胞可以被一个更简单的patchify层à la ViT(à la是啥东西,真的不知道他在说什么玩意儿)替代,这将导致类似的性能。我们将在网络中使用patchify干( 非重叠卷积)。
在这一部分中,作者尝试采用ResNeXt的思想,它比普通的ResNet具有更好的FLOPs/准确性权衡。ResNeXt核心部分是分组卷积,其中卷积滤波器被分成不同的组。在高层次上,ResNeXt的指导原则是使用更多的组,扩大宽度。更准确地说,ResNeXt在bottleneck块中对 3*3 conv层使用了分组卷积。这样做可以显著地降低FLOPs,通过扩大网络宽度来弥补容量损失。
在文章的例子中,作者使用深度卷积,这是分组卷积的一种特殊情况,分组的数量等于通道的数量。Depthwise conv已经由MobileNet和Xception推广。作者注意到,深度卷积类似于自注意中的加权和操作,其操作基于每个通道,即只在空间维度上混合信息。depth-wise conv和 1*1 conv的组合导致了一个空间的分离和通道的混合,这是vision transformer共有的属性,其中每个操作要么混合了空间或通道维度的信息,但不同时混合。深度卷积的使用有效地减少了网络的FLOPs,和预期的一样,精度。按照ResNeXt中提出的策略,我们将网络宽度增加到与Swin-T相同的通道数量(从64个增加到96个)。这使得网络性能达到80.5%,FLOPs增加到5.3G。我们现在将采用ResNeXt设计。
每个Transformer块的一个重要设计是,它创建了一个倒置的瓶颈,即,MLP块的隐藏尺寸是输入尺寸的四倍宽。
有趣的是,这种Transformer设计与反向瓶颈设计有关,在ConvNets中使用的扩展比为4。这个想法是由MobileNetV2推广,随后在几个先进的ConvNet架构中获得了支持。
这里作者将探讨反向瓶颈设计。图1(a)到(b)说明了配置。尽管深度卷积层的FLOPs增加了,但这一变化使整个网络FLOPs减少到4.6G,这是由于下采样残差块使用快捷的 1*1 conv层使得FLOPs显著减少。有趣的是,这会略微提高性能(从80.5%提高到80.6%)。在ResNet-200 / Swin-B模式中,这一步带来了更多的收益(81.9%至82.6%),同时也减少了FLOPs。现在我们将使用反向瓶颈。
在这一部分的探索中,我们将重点关注大型卷积核的行为。Vision Transformer最与众不同的一个方面是它们的非局部自我关注,这使得每一层都有一个全局的接收域。虽然大的卷积核在过去已经被ConvNets使用,但黄金标准(由VGGNet推广)是堆叠小卷积核( 3*3 )的转换层,这在现代gpu上具有高效的硬件实现。虽然Swin-T重新将本地窗口引入到自注意力模块中,但窗口的大小至少是 7*7 ,明显大于ResNe(X)t的 3*3 大小。在这里,我们将重新讨论在ConvNets中使用大型核大小的卷积。
Moving up depthwise conv layer.要探索大型内核,一个先决条件是向上移动深度转换层的位置(图1 (b)到(c))。这个设计决策在transformer中也很明显:MSA块被放置在MLP层之前。由于我们有一个倒置的瓶颈块,这是一个自然的设计选择,复杂/低效的模块(MSA,大内核conv)将有更少的通道,而高效、密集的 1*1 层将做繁重的工作。这个中间步骤将FLOPs降低到4.1G,导致性能暂时下降到79.9%。
Increasing the kernel size.有了所有这些准备,采用更大尺寸的卷积核的好处是明显的。我们实验了几种内核尺寸包括3、5、7、9和11,网络的性能从79.9% 3*3 提高到80.6% 7*7,但网络的FLOPs基本保持不变。此外,我们观察到卷积核大小在 7*7 时候性能达到饱和点。我们在大容量模型中也验证了这一行为:当我们将内核大小增加到 7*7 时,ResNet-200机制模型并没有显示出进一步的增益。(这里在其他经典网络模型中已经证明,前面也说了,VGG就是 7*7 )。We will use 7*7 depthwise conv in each block。有趣的是,视觉Transformer中很大一部分的设计决策可以映射到ConvNet设计案例中。
经过前面的改动,模型的性能已经提升到80%以上,此时改动后的ResNet50也和Swin-T在整体结构上很类似了,下面我们开始关注一些微观设计上的差异,或者说是layer级别的不同。 首先是激活函数,CNN模型一般采用ReLU,而transformer模型常常采用GELU,两者的区别如下图所示。这里把激活函数都从ReLU改成GELU,模型效果没有变化(80.6%)。
减少激活层和归一化层如下图示,这里只保留中间1x1 conv之后的GELU,就和Swin-T基本保持一致了,这个变动使模型性能从80.6%提升至81.3%。
对于norm层,也存在和激活函数一样的问题,transformer中只在self-attention和MLP的开始采用了LayerNorm,而ResNet每个conv之后采用BatchNorm,比transformer多一个norm层。这里去掉其它的BatchNorm,只保留中间1x1 conv前的BatchNorm,此时模型性能有0.1%的提升。实际上要和 transformer 保持一致,应该在block最开始增加一个BatchNorm,但是这个并没有提升性能,所以最终只留下了一个norm层。另外,transformer的norm层采用 LayerNorm,而CNN常采用BatchNorm,一般情况下BatchNorm要比LayerNorm效果要好,但是BatchNorm受batch size的影响较大。这里将BatchNorm替换成LayerNorm后,模型性能只有微弱的下降(80.5%)。
最后一个差异是下采样,ResNet中的下采样一般放在每个stage的最开始的block中,采用 stride=2 的3x3 conv;
但是ConvNeXt 采用分离的下采样去近似 Swin Transform的 Patch Merging layer,即下采样是放在两个stage之间,通过一个stride=2的 2x2 conv。但是实验发现,如果直接改用Swin-T的下采样,会出现训练发散问题,解决的办法是在添加几个norm层:在stem之后,每个下采样层之前以及global avg pooling之后都增加一个LayerNom(Swin-T也是这样做的)。最终模型的性能提升至82.0%,超过Swin-T(81.3%)。
根据最大池化的操作,取每个块中的最大值,而其他元素将不会进入下一层。众所周知,CNN卷积核可以理解为在提取特征,对于最大池化取最大值,可以理解为提取特征图中响应最强烈的部分进入下一层,而其他特征进入待定状态(之所以说待定,是因为当回传梯度更新一次参数和权重后,最大元素可能就不是在原来的位置取到了)。
一般而言,前景的亮度会高于背景,因此,正如前面提到最大池化具有提取主要特征、突出前景的作用。但在个别场合,前景暗于背景时,最大池化就不具备突出前景的作用了。因此,当特征中只有部分信息比较有用时,使用最大池化。如网络前面的层,图像存在噪声和很多无用的背景信息,常使用最大池化。同理,平均池化取每个块的平均值,提取特征图中所有特征的信息进入下一层。因此当特征中所有信息都比较有用时,使用平均池化。如网络最后几层,最常见的是进入分类部分的全连接层前,常常都使用平均池化。这是因为最后几层都包含了比较丰富的语义信息,使用最大池化会丢失很多重要信息。
BN 在图像领域一般优于 LN, LN 更适合 RNNBN 比较适用的场景是:每个 mini-batch 比较大,数据分布比较接近。在进行训练之前,要做好充分的 shuffle. 否则效果会差很多。LN 针对单个训练样本进行,不依赖于其他数据,因此可以避免 BN 中受 mini-batch 数据分布影响的问题,可以用于 小mini-batch场景、动态网络场景和 RNN,特别是自然语言处理领域。此外,LN 不需要保存 mini-batch 的均值和方差,节省了额外的存储空间。
参考:A ConvNet for the 2020s 论文解读