看明白这张图就理解resnet了
可见F(x) + x会存在两种不匹配的情况:
channel和size
要利用conv进行改变
注意看代码中in_planes != self.expansion*planes这个条件
以bottleneck作为例子:
输入是256dim,经过了block第一层1*1卷积之后变成了64dim,因此in_channel = 4 * out_channel
PS:包括明确一点,这个判定只是在block开始的时候,内部不进行判定(这里构造block是作为整体获得的)
if stride != 1 or in_planes != self.expansion*planes:
# stride进行尺寸变换(变小)
# self.expansion进行通道变化(变宽)
self.shortcut = nn.Sequential(
nn.Conv2d(in_planes, self.expansion*planes, kernel_size=1, stride=stride, bias=False),
nn.BatchNorm2d(self.expansion*planes)
)
注意看注释,仅仅conv3-1, 4-1, 5-1存在下采样图像尺寸减半
conv2-1 stride = 1 下采样依靠的maxpooling