这篇论文的数据预处理方式非常简单,就是将图片抠出中间的256×256的部分,并且减去各个通道的像素值的均值。并不对数据的方差做什么处理,就是这篇论文比较新鲜的地方了,我们知道在传统的模型中,我们大多数都比较喜欢让数据的分布满足一个均值为0,方差为1的一个大致分布,而这里论文作者就说了,“俺们的模型贼NB,0均值就够了,方差啥的无所谓,就是这么6”(大概这个意思啦,不是原文┓(\'∀\')┏)。
大家如果读过论文的话,应该可以大致了解过AlexNet的模型的规模,实际上还是很大的。论文作者也提到过,对于这个如此庞大的模型(对于当时来说),即使使用的数据集这么大,模型的过拟合的风险还是蛮高的,因此仍然需要通过数据增强,来扩展训练集。所使用的数据增强方法如下:
随机抠图:经过预处理后,我们得到了256×256的图片,为了进一步增强数据,论文提到从这个256×256的图片中,每一次训练都随机抠出来一个224×224的图片作为实际的网络输入,这样就保证每一次用某一张图片输入网络的时候,实际输入的图片都会稍稍有一点不一样,从而起到数据增强的作用。不过因为我们这里使用的数据集不是ImageNet而是cifar-10,后者的图片大小也就32×32,所以这里我就直接把图片扩展到224×224了,当然也可以先扩展到256×256然后自己随机裁剪一下,这个在PIL以及OpenCV中都是支持的。然后均值实际上在《Deep Learning with Pytorch》这本书里已经算过了,所以我就不算了,感兴趣的可以自己算一下。图片处理器的代码就放在下面:
picProcessor = T.Compose([ T.Resize(224), T.ToTensor(), T.Normalize( mean = [0.4915, 0.4823, 0.4468], std=[1.0, 1.0, 1.0] ) ])PCA成分叠加:论文提到,为了从像素层面进行数据的增强,首先先对整个训练集的各个通道的像素值计算各个通道的主成分,然后再将主成分添加随机数来叠加到训练集的图片上。这样每一次使用的图片即使是由上一个随机抠图的步骤抠到完全相同位置的图片,实际的像素内容也是不太一样的,因此起到了数据增强的作用。具体的叠加方式我建议大家看一下论文,因为这里复现工作没使用ImageNet数据集,就简单使用了一下cifar-10,所以这里提到的两个数据增强的方法就都不用了,如果大家有兴趣的话可以自己实现一下,反正PCA在python的sklearn库是已经实现了的,调包就完事了┓(\'∀\')┏
这样,关于数据预处理以及数据增强的部分就基本上这样了,也基本没有什么实现难点,所以我们还是赶快进入模型重点吧( ̄▽ ̄)
网络结构部分网络的结构其实蛮简单的,但是在读论文以及看论文附图的时候有两个比较要命的问题:
论文是基于两个GPU进行的描述,但是我们现在没必要把这个模型分开,现在1050以上的显卡基本上显存都在4G以上,完全装得下的,所以我们要把论文里面的模型的卷积层的通道数扩大成两倍,这样才和论文的实际模型描述是一致的
论文的模型附图······讲道理我当时看半天没看懂到底咋回事,然后去其他人的博客里找了找,才找到一个感觉是那么回事的图,所以如果原论文的图看不懂的,就来看我之后要用到的那个图。
那么接下来我们就来看一下这个经典的AlexNet吧!
网络整体结构如果大家看过原作论文了,那么应该对下面的图片感到很熟悉吧:
怎么说呢,这个图片倒是把卷积层的卷积核尺寸以及特征图通道数都写的蛮清楚的,然而你会发现他的什么池化啊还有一些卷积计算的尺寸完全对不上,论文把图整的太简单了,所以导致我们后面的人在看的时候可能有点看不太懂。并且他这个图是放在两个GPU上的版本,而我们现在只用一个GPU就完全够用了,因此我们可以看一下下面的这个图: