ResNet:
ResNet为什么能训练很深的网路:ResNet引入了加法从而在反向传播的时候后面层的梯度是加上前面层的梯度,使得梯度不会很小,解决了梯度消失的问题;
DenseNet:
由于DenseNet对输入进行cat操作,一个直观的影响就是每一层学到的feature map都能被之后所有层直接使用,这使得特征可以在整个网络中重用,也使得模型更加简洁.
DenseNet代码:
1.稠密块:一个稠密块由多个卷积块组成,每个卷积块使用相同数量的输出通道。 然而,在前向传播中,我们将每个卷积块的输入和输出在通道维上连结。
我们定义一个
DenseBlock
有2个卷机层且输出通道数为10。 使用通道数为3的输入时,我们会得到通道数为3+2×10=23的输出;那么输入层3channel;第一层就是3+10=13层;第二层就是3+10+10=23层;class DenseBlock(nn.Module): def __init__(self, num_convs, input_channels, num_channels): super(DenseBlock, self).__init__() layer = [] for i in range(num_convs): layer.append(conv_block( num_channels * i + input_channels, num_channels)) self.net = nn.Sequential(*layer) def forward(self, X): for blk in self.net: Y = blk(X) # 连接通道维度上每个块的输入和输出 X = torch.cat((X, Y), dim=1) return X
2.过渡层:它通过1×1卷积层来减小通道数,并使用步幅为2的平均汇聚层减半高和宽,从而进一步降低模型复杂度。
def transition_block(input_channels, num_channels): return nn.Sequential( nn.BatchNorm2d(input_channels), nn.ReLU(), nn.Conv2d(input_channels, num_channels, kernel_size=1), nn.AvgPool2d(kernel_size=2, stride=2))