大家好,又见面了,我是你们的朋友全栈君。
本文主要对CNN领域的经典模型进行汇总,算是对近期的学习做一个小总结。
基础知识
作为深度学习的基础,神经网络这个算法是必须要有深入的了解的,这里不介绍太多,简单介绍一下原理和单个神经元的结构:
一、BP神经网络的概念
BP神经网络是一种多层的前馈神经网络,其主要的特点是:信号是前向传播的,而误差是反向传播的。具体来说,对于如下的只含一个隐层的神经网络模型:
BP神经网络的过程主要分为两个阶段,第一阶段是信号的前向传播,从输入层经过隐含层,最后到达输出层;第二阶段是误差的反向传播,从输出层到隐含层,最后到输入层,依次调节隐含层到输出层的权重和偏置,输入层到隐含层的权重和偏置。
二、单个神经元的结构
主要是通过对输入信号的加权求和加偏置(加权求和对应的w,偏置对应的b),然后通过通过激活函数引入非线性元素并将结果映射至0——1之间的数值(比如sigmoid函数)。具体见下图:
图片来源于台大 李宏毅 300页 PPT https://www.slideshare.net/tw_dsconf/ss-62245351 (记得FQ) 个人觉得这个PPT非常不错,从浅到深,讲的也十分具体,有时间可以仔细看看。
CNN模型汇总
一、LeNet5 模型
LeNet5 诞生于 1994 年,是最早的卷积神经网络之一,并且推动了深度学习领域的发展。自从 1988 年开始,在许多次成功的迭代后,这项由 Yann LeCun 完成的开拓性成果被命名为 LeNet5(参见:Gradient-Based Learning Applied to Document Recognition)。
LeNet5 的架构基于这样的观点:(尤其是)图像的特征分布在整张图像上,以及带有可学习参数的卷积是一种用少量参数在多个位置上提取相似特征的有效方式。在那时候,没有 GPU 帮助训练,甚至 CPU 的速度也很慢。因此,能够保存参数以及计算过程是一个关键进展。这和将每个像素用作一个大型多层神经网络的单独输入相反。LeNet5 阐述了那些像素不应该被使用在第一层,因为图像具有很强的空间相关性,而使用图像中独立的像素作为不同的输入特征则利用不到这些相关性。
LeNet5特征能够总结为如下几点: 1)卷积神经网络使用三个层作为一个系列: 卷积,池化,非线性 2) 使用卷积提取空间特征 3)使用映射到空间均值下采样(subsample) 4)双曲线(tanh)或S型(sigmoid)形式的非线性 5)多层神经网络(MLP)作为最后的分类器 6)层与层之间的稀疏连接矩阵避免大的计算成本
总体看来,这个网络是最近大量神经网络架构的起点,并且也给这个领域带来了许多灵感。 从 1998 年到 2010 年神经网络处于孵化阶段。大多数人没有意识到它们不断增长的力量,与此同时其他研究者则进展缓慢。由于手机相机以及便宜的数字相机的出现,越来越多的数据可被利用。并且计算能力也在成长,CPU 变得更快,GPU 变成了多种用途的计算工具。这些趋势使得神经网络有所进展,虽然速度很慢。数据和计算能力使得神经网络能完成的任务越来越有趣。之后一切变得清晰起来……
二、AlexNet 模型
2012年,Hinton的学生Alex Krizhevsky提出了深度卷积神经网络模型AlexNet,它可以算是LeNet的一种更深更宽的版本。AlexNet中包含了几个比较新的技术点,也首次在CNN中成功应用了ReLU、Dropout和LRN等Trick。同时AlexNet也使用了GPU进行运算加速,作者开源了他们在GPU上训练卷积神经网络的CUDA代码。AlexNet包含了6亿3000万个连接,6000万个参数和65万个神经元,拥有5个卷积层,其中3个卷积层后面连接了最大池化层,最后还有3个全连接层。
AlexNet以显著的优势赢得了竞争激烈的ILSVRC 2012比赛,top-5的错误率降低至了16.4%,相比第二名的成绩26.2%错误率有了巨大的提升。AlexNet可以说是神经网络在低谷期后的第一次发声,确立了深度学习(深度卷积网络)在计算机视觉的统治地位,同时也推动了深度学习在语音识别、自然语言处理、强化学习等领域的拓展。
AlexNet将LeNet的思想发扬光大,把CNN的基本原理应用到了很深很宽的网络中。AlexNet主要使用到的新技术点如下:
(1)成功使用ReLU作为CNN的激活函数,并验证其效果在较深的网络超过了Sigmoid,成功解决了Sigmoid在网络较深时的梯度弥散问题。虽然ReLU激活函数在很久之前就被提出了,但是直到AlexNet的出现才将其发扬光大。 (2)训练时使用Dropout随机忽略一部分神经元,以避免模型过拟合。Dropout虽有单独的论文论述,但是AlexNet将其实用化,通过实践证实了它的效果。在AlexNet中主要是最后几个全连接层使用了Dropout。 (3)在CNN中使用重叠的最大池化。此前CNN中普遍使用平均池化,AlexNet全部使用最大池化,避免平均池化的模糊化效果。并且AlexNet中提出让步长比池化核的尺寸小,这样池化层的输出之间会有重叠和覆盖,提升了特征的丰富性。 (4)提出了LRN层,对局部神经元的活动创建竞争机制,使得其中响应比较大的值变得相对更大,并抑制其他反馈较小的神经元,增强了模型的泛化能力。 (5)使用CUDA加速深度卷积网络的训练,利用GPU强大的并行计算能力,处理神经网络训练时大量的矩阵运算。AlexNet使用了两块GTX 580 GPU进行训练,单个GTX 580只有3GB显存,这限制了可训练的网络的最大规模。因此作者将AlexNet分布在两个GPU上,在每个GPU的显存中储存一半的神经元的参数。因为GPU之间通信方便,可以互相访问显存,而不需要通过主机内存,所以同时使用多块GPU也是非常高效的。同时,AlexNet的设计让GPU之间的通信只在网络的某些层进行,控制了通信的性能损耗。 (6)数据增强,随机地从256´256的原始图像中截取224´224大小的区域(以及水平翻转的镜像),相当于增加了(256-224)2´2=2048倍的数据量。如果没有数据增强,仅靠原始的数据量,参数众多的CNN会陷入过拟合中,使用了数据增强后可以大大减轻过拟合,提升泛化能力。进行预测时,则是取图片的四个角加中间共5个位置,并进行左右翻转,一共获得10张图片,对他们进行预测并对10次结果求均值。同时,AlexNet论文中提到了会对图像的RGB数据进行PCA处理,并对主成分做一个标准差为0.1的高斯扰动,增加一些噪声,这个Trick可以让错误率再下降1%。
整个AlexNet有8个需要训练参数的层(不包括池化层和LRN层),前5层为卷积层,后3层为全连接层,如图4所示。AlexNet最后一层是有1000类输出的Softmax层用作分类。 LRN层出现在第1个及第2个卷积层后,而最大池化层出现在两个LRN层及最后一个卷积层后。ReLU激活函数则应用在这8层每一层的后面。因为AlexNet训练时使用了两块GPU,因此这个结构图中不少组件都被拆为了两部分。现在我们GPU的显存可以放下全部模型参数,因此只考虑一块GPU的情况即可。
整个网络呈一个金字塔结构,具体来说:
- 输入图片是224*224像素的三通道图片;
- 第一层使用11*11的卷积核,滑动步长为4个像素,输出为96个特征图并进行最大值池化;
- 第二层使用5*5卷积核,卷积产生256个特征图,并进行最大池化;
- 第三层,第四层均使用3*3卷积核,输出384个特征图;
- 第五层使用3*3卷积层,输出256个特征图,并进行池化;
- 第六层,第七层为全连接层,分别包含4096个隐层,也就是说,到全连接层时只剩4096个特征值;
- 最终,第八层为softmax层,得到最终的分类结果。
三、VGG 模型
来自牛津大学的 VGG 网络(参见:Very Deep Convolutional Networks for Large-Scale Image Recognition)是第一个在各个卷积层使用更小的 3×3 过滤器(filter),并把它们组合作为一个卷积序列进行处理的网络。
这看来和 LeNet 的原理相反,其中是大的卷积被用来获取一张图像中相似特征。和 AlexNet 的 9×9 或 11×11 过滤器不同,过滤器开始变得更小,离 LeNet 竭力所要避免的臭名昭著的 1×1 卷积异常接近——至少在该网络的第一层是这样。但是 VGG 巨大的进展是通过依次采用多个 3×3 卷积,能够模仿出更大的感受野(receptive field)的效果,例如 5×5 与 7×7。这些思想也被用在了最近更多的网络架构中,如 Inception 与 ResNet。
VGGNet论文中全部使用了3´3的卷积核和2´2的池化核,通过不断加深网络结构来提升性能。图6所示为VGGNet各级别的网络结构图,图7所示为每一级别的参数量,从11层的网络一直到19层的网络都有详尽的性能测试。虽然从A到E每一级网络逐渐变深,但是网络的参数量并没有增长很多,这是因为参数量主要都消耗在最后3个全连接层。前面的卷积部分虽然很深,但是消耗的参数量不大,不过训练比较耗时的部分依然是卷积,因其计算量比较大。这其中的D、E也就是我们常说的VGGNet-16和VGGNet-19。C很有意思,相比B多了几个1´1的卷积层,1´1卷积的意义主要在于线性变换,而输入通道数和输出通道数不变,没有发生降维。
VGGNet拥有5段卷积,每一段内有2~3个卷积层,同时每段尾部会连接一个最大池化层用来缩小图片尺寸。每段内的卷积核数量一样,越靠后的段的卷积核数量越多:64 – 128 – 256 – 512 – 512。其中经常出现多个完全一样的3´3的卷积层堆叠在一起的情况,这其实是非常有用的设计。如图8所示,两个3´3的卷积层串联相当于1个5´5的卷积层,即一个像素会跟周围5´5的像素产生关联,可以说感受野大小为5´5。而3个3´3的卷积层串联的效果则相当于1个7´7的卷积层。除此之外,3个串联的3´3的卷积层,拥有比1个7´7的卷积层更少的参数量,只有后者的。最重要的是,3个3´3的卷积层拥有比1个7´7的卷积层更多的非线性变换(前者可以使用三次ReLU激活函数,而后者只有一次),使得CNN对特征的学习能力更强。
同时,作者在对比各级网络时总结出了以下几个观点。 (1)LRN层作用不大。 (2)越深的网络效果越好。 (3)1´1的卷积也是很有效的,但是没有3´3的卷积好,大一些的卷积核可以学习更大的空间特征。
总的来说,在网络设计思路上,VGGNet是继承了AlexNet的思路,以AlexNet为基础,尝试建立一个层次更多,深度更深的网络。其网络结构一样可以由8个层次所构成,也是5组卷积层,3层全连接层。最主要的区别在于,VGGNet的每个卷积层并不是只做一次卷积操作,而是连续卷积2~4次。具体结构上的差别见下表(包括其它网络结构和VGG16与VGG19):
四、GoogleNet模型
在VGGNets中我们了解到,如果网络的层数更多,深度更深,就会得到更好的结果。但是随着模型越来越复杂,参数越来越多,也会面临很多问题。一方面,是更深的网络需要更多的数据才能有更好的效果,否则就比较容易过拟合。另一方面,复杂的网络意味着更大的计算量,这对于应用来说非常不利。在一些对实时性要求非常高的应用中,比如自动驾驶,要求参数足够少,计算速度足够快。所以,减少参数也是一个重要的课题。因此,为了能更有效地扩展网络地复杂度,Google的大神们启动了Inception项目,GoogleNet就是它的第一个版本(目前共有4个版本)。
正如前面在对比AlexNet和VGGNets的结构时提到的,对于卷积核大小的选择是需要经验和大量实验才可以确定的,到底是选3*3呢,还是5*5或者7*7?这个问题并没有一种明确的思路。这里的做法是跳出直线加深网络层数的思路,通过增加“宽度”的方式增加网络复杂度,避免陷入卷积核选择的陷阱,让程序自己学习如何选择卷积核。具体来说中,是在每一个卷积层,并行使用1*1卷积核,3*3卷积核,5*5卷积核和池化,同时提取不同尺度的特征,然后通过1*1的卷积核对每一个分支进行降维后,最后将结果合并拼接在一起。直观地看起来,好像结构复杂了很多,本来只要一两个卷积就可以完成地计算,现在却要使用四五种不同地操作。但是仔细分析可以发现,这样地设计不仅减少了参数地数量,而且由于增加了网络地“宽度”,网络对多种尺度地适应性就更好了(GoogleNet中地block结构如图:)
在这个结构中,1*1卷积扮演了非常重要地角色,1*1卷积并没有对图像本身产生什么影响,在数学上仅仅是最简单地矩阵乘法操作,其最重要的作用在于降低特征图的数量以达到降维的目的。由于有了1*1卷积的存在,才使得网络可以在不增加参数数量级的情况下可以增加复杂度。
这里给出完整的GoogleNet模型结构:
这里补充两个注意点: 1. 对于不同的卷积核,要取不同的滑动步长,以使得他们输出的特征图大小相同,便于后一步的操作; 2. 在CNN中,1*1的卷积核最主要的作用在于改变通道数,比如,原图像 3*64*64的rgb,通过5个1X1卷积核就变成了5*64*64.用5个卷积核代替了原来RGB三通道的表示方法。因此,该卷积核既可以升维又可以降维;
Inception项目的其它几个版本这里做一下简要的概述,不过多讨论: 1.Inception-v2是在第一代的GoogleNet基础上加入了批标准化(Batch Normalization)技术。其具体做法是,对mini-batch中所有的信号量进行统一的归一化,使得一个批次中所有的信号量符合均值为0,方差为1的高斯分布。需要注意的是,在tensorflow中,使用批标准化技术要在激活函数之前,否则作用会打一定的折扣;
2.Inception-v3在之前的版本上又有提高。其最核心的思想是将卷积核操作继续分解成更小的卷积核。首先,比如,借鉴VGGNets的思路,5*5的卷积可以由连续2层3*3卷积所替代,这样既减少了参数数量,也进一步加快了计算速度。这样的好处是,在经过这样的转换后,不但参数数量进一步减少,计算速度更快,而且网络的深度也加深了,增加了非线性表达能力。
五、ResNets模型
对于深度神经网络来说,VGGNets证明了加深网络层次是提高精度的有效手段,但是由于梯度弥散的问题导致网络深度无法持续加深。梯度弥散问题是由于在反向传播过程中误差不断累积,导致在最初的几层梯度值几乎为0,从而无法收敛。经过测试,20层以上的深层网络,会随着层数的增加,收敛效果越来越差,50层的网络是20层的网络所得错误率的一倍。这一现象称为深度网络的退化问题。
退化问题其实说明,不是所有的系统都能很容易的被优化。难道网络的深度的增加到此为止了吗?ResNets告诉我们残差网络是一种避免梯度消失的更容易优化的结构。
熟悉机器学习算法的都可以理解,神经网络实际上是将一个空间维度的向量x,经过非线性变换H(x)映射到另外一个空间维度中。但通过前面的观察会意识到H(x)非常难以优化,所以尝试转而求H(x)的残差形式F(x)=H(x)-x。假设求解F(x)=H(x)-x。假设求解F(x)会比求H(x)要简单一些的话,就可以通过F(x) x来达到最终1的目标。
从实际实验的结果来看,残差网络的效果是非常明显的。如论文里所说,类似VGGNet的结构在超过20个参数层以后,收敛效果会大打折扣,准确率比较差,但是简单地加入一些“捷径”(shortcut)连接边后,使其转变为残差结构,收敛效果都急剧提高,精度也随着训练次数地增加持续提高,并且不断加深网络深度还可以持续提高准确率,残差网络与VGG结构地对比如图所示:
ResNets的成功,使整个卷积神经网络的研究上了一个新的台阶,inception也将残差结构融入其中,实现了更优秀的模型inception-v4。
注:这个ResNets模型我不是太能看明白,不太理解为什么残差形式F(x)=H(x)-x要比H(x)容易求解,留作疑问,若有人看到这篇博文,欢迎前来讨论!
发布者:全栈程序员栈长,转载请注明出处:https://javaforall.cn/125150.html原文链接:https://javaforall.cn