经典卷积神经网络之ResNet

        随着卷积神经网络深度的不断增加,训练的难度也在不断增大,同时会出现梯度消失的问题。而ResNet就是为了解决这些问题,它能够保证改造后的模型至少不会比原来的模型差。
        残差网络模块:
在这里插入图片描述
        我们可以看到输入传递到残差网络模块之后,会首先通过一些卷积操作,然后将其输出与原来的输入进行连接,得到残差网络的输出。这里要求,卷积之后的输出维度,要与原来输入的维度保持一致。
        主要有两种方式:一种即简单地将X相对Y缺失的通道直接补零从而使其能够相对齐的方式,另一种则是通过使用1x1的conv从而使得最终输入与输出的通道达到一致的方式。(这里的加法是元素级相加,必须保证卷积的输出形状与原始输入形状一致)(通常采用第二种方式)
        瓶颈结构:
在这里插入图片描述
        为了实际计算的考虑,作者提出了一种bottleneck的结构块来代替常规的Resedual block,它像Inception网络那样通过使用1x1 conv来巧妙地缩减或扩张feature map维度从而使得我们的3x3 conv的filters数目不受外界即上一层输入的影响,自然它的输出也不会影响到下一层module。通过瓶颈结构,我们可以搭建ResNet网络。在ResNet网络中,主要存在两个模块:Conv Block、Identity Block。
在这里插入图片描述
        可以看到两者之间的主要区别就是残差边有没有做操作,Conv Block的残差边做了卷积操作,因此它的输入和输出的维度是不一样的,我们不能用它进行连续的串联,它的主要功能就是来改变网络的维度。而Identity Block的残差边没有做操作,因此它的输入和输出的维度一致,主要的功能就是做连续的串联,增加网络的深度。
        下面解释一下,为什么ResNet可以解决梯度消失的问题,为什么ResNet搭建模型的效果至少不会比原来的差:
在这里插入图片描述
        上图,就是瓶颈结构
在这里插入图片描述
        公式中的xl表示的是瓶颈结构的输入,XL表示的是瓶颈结构的输出,F(x)表示的是residual,它是一个普通的正向传播的过程。
        输出是这两部分的和:H(x) = F(x)(就是residual)+ x(就是shortcut,此代码shortcut部分做了一次卷积,也可以不做)
        之所以可以避免梯度消失问题,是因为反向传播时,ε 代表的是 loss 方程,由链式求导法得:
在这里插入图片描述
        从上图我们可以知道,即使residual部分的梯度为0,整个瓶颈机构的梯度也不会为0,从而避免的梯度消失的问题,而且使用瓶颈结构至少也不会比原来的模型效果差。
        总结:从LeNet、AlexNet到VggNet以至GoogLeNet都是在不断的增加网络的深度来达到提高卷积神经网络的表达能力,但是随着网络的深度越来越深,模型的训练越来越难,而且一味地增加网络的深度并不能够进一步的带来性能的提升,反而会导致网络的收敛变得更慢。而ResNet主要就是解决了随着网络深度的加深,模型收敛难的问题,有了ResNet之后,训练一个更深层次的网络的不再是一个问题。

### 卷积神经网络ResNet模型实现与使用 #### 背景介绍 卷积神经网络(CNNs)架构高度依赖于输入据的性质以及预期输出大小。对于图像或音频序列等不同类型的输入,存在多种常见的卷积神经网络结构,其中包括ResNet[^1]。 #### ResNet简介 ResNet(残差网络),由微软研究院的研究人员提出,在ImageNet竞赛中取得了优异的成绩。该模型通过引入跳跃连接解决了深层网络训练中的梯度消失问题,使得可以构建更深更复杂的网络而不会导致性能下降。 #### 实现ResNet模型 下面是一个简单的基于PyTorch框架下的ResNet模型实现: ```python import torch from torchvision import models class SimpleResNet(torch.nn.Module): def __init__(self, num_classes=1000): super(SimpleResNet, self).__init__() # 使用预定义好的resnet50作为基础特征提取器 resnet = models.resnet50(pretrained=True) # 替换最后一层全连接层以适应新的分类任务 fc_in_features = resnet.fc.in_features resnet.fc = torch.nn.Linear(fc_in_features, num_classes) self.model = resnet def forward(self, x): return self.model(x) if __name__ == "__main__": device = 'cuda' if torch.cuda.is_available() else 'cpu' net = SimpleResNet(num_classes=10).to(device) dummy_input = torch.randn((1, 3, 224, 224)).to(device) output = net(dummy_input) print(output.shape) # 应打印torch.Size([1, 10]) ``` 这段代码展示了如何利用`torchvision.models`库快速搭建一个用于特定类别预测的任务上的简化版ResNet模型,并进行了基本测试。 #### 据准备 为了能够有效地应用上述创建的ResNet模型来进行时间序列预测或其他视觉识别任务,需要准备好合适的据集并对其进行适当处理。这通常涉及到将原始图片转换成适合喂入网络的形式——即标准化后的张量形式。此外还需要考虑批量加载机制来提高效率[^3]。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值