关于ResNet 网络的一些思考和看法

resnet 现在在深度学习上面已经成了一个很成熟的神经网络结构了。现在许多学习任务基本都是用resnet来做backbone做各种任务。说起resnet大家的第一映像是什么?是不是就是那一根跳跃连接的线图1。如果再问你一下为什么加这根线呢?研究深的人也许会说这是为了解决梯度消失/爆炸的问题。最后大家都会说了解到这里基本就够了,会用就行了。如果 现在跟你说你的理解错了,你会怎么说,你会说这不可能。我一直都这么理解的呀。其实说心里话,一开始我也是这么理解的。

                                                                                 图1 resnet block 模块

下面我们来一点点的解释一下为什么这个观点错了。其实在论文中作者也说了这个问题,如图2,我们有这种认为大概率是因为论文看的时间长了,忘了一些其中的细节了。论文中的原话是说梯度消失、爆炸问题已经已经被"normalized initialization"和"intermediate normalization layers"技术解决了。我们当初看的时候,也许只是“恩”的一声就过去了。

图2 论文中的原话

那么我们现在来简单的看看,这个问题到底是怎么被解决的,要回答这个问题前,我们了解一下什么叫梯度消失/爆炸。

现在我们在进行深度神经网络学习的时候基本都是用了反向传播的方法来进行学习,这其中传递的就是梯度,当梯度消失或者爆炸的时候基本这个网络就很难学习到东西了。

一项一项来,梯度消失是什么,说到反向传播,大家脑海里有什么?是不是就是那一串乘积操作。对,就是那个,我们现在想象一下那个一串乘积操作,当其中的项是每一项的输入值都是恒小于1的时候,大家就可以想象到最后这个乘积到最后基本就太小了,当小于精度的时候计算机默认这就没有了。最后就会学习到噪声。反过来当这个乘积的项每一项的输入都是大于1的时候,最后的结果就会越来越大。最后就NAN了。

因此为了解决这个问题,大家不管在使用什么框架pytorch/keras/tensorflow的时候都会加上BN的操作,这就为了控制每一项的值,不至于过大也不至于过小。这样慢慢就解决了梯度的问题了。那么我们现在又回到我们最开始的问题,resnent的那一个跳跃到底有什么用呢?

其实大家都知道当模型网络越来越深的时候模型的能力反而下降了。

这里的具体细节大家可以去看一下论文,这里我就不细说了。其实大家按正常的逻辑想想,当网络越来深的时候,理论上不应该越来越差呀,至少应该和前面浅层的模型一样的能力呀。我后面的网络加深的网络我都变成1 然后都是恒等有前面,这样不就跟前面一样了吗?这里恰恰是问题的关键,就像大家的爱情一样,去了就回不来了。因为经过太多的非线性的激活,真的很难再回去了。因此为了表示一个恒等真的很难,因此就让学习到一个x=f(x)+x。等f(x)等于0的时候不就恒等了呀。这就是残差的学习,一开始大家学习 f(x)+x 当网络越来越深的时候f(x)逐渐等于0了。这样就有了恒等的能力了。因此resnet的网络设计说到底就是为了让深度学习的神经网络有这个恒等能力。

当然这里的F(x)也是有很多窍门的,许多人利用这个F(x)也发布了许多好的论文。

猜你喜欢

转载自blog.csdn.net/nijiayan123/article/details/105879703