欢迎光临散文网 会员登陆 & 注册

20 卷积层里的填充和步幅【动手学深度学习v2】

2023-07-19 18:10 作者:月芜SA  | 我要投稿

使用更大的卷积核可以更快地减小输出大小,在层数较大时,图像会变得过小。

解决方案1:填充

不填充的话边缘上用到的信息次数没有中间的多,填充后,可以增多边缘信息的读取次数。

下图展示了常用的填充列数和行数,基本思路是保持输出和输入数据形状不变。


解决方案2:步幅

步幅对输出形状的影响(调整步幅通常可以将数据成倍缩小)

卷积核大小、数据填充量、步幅等都是卷积层的超参数

总结:


代码实现

在所有侧边填充一个像素

import torch
from torch import nn


# 为了方便起见,我们定义了一个计算卷积层的函数。
# 此函数初始化卷积层权重,并对输入和输出提高和缩减相应的维数
def comp_conv2d(conv2d, X):
    # 这里的(1,1)表示批量大小和通道数都是1
    X = X.reshape((1, 1) + X.shape)
    #此步是将二维数据X(8,8)转化为四维数据X(1,1,8,8)
    Y = conv2d(X)
    # 省略前两个维度:批量大小和通道
    return Y.reshape(Y.shape[2:])

# 请注意,这里每边都填充了1行或1列,因此总共添加了2行或2列
conv2d = nn.Conv2d(1, 1, kernel_size=3, padding=1)
X = torch.rand(size=(8, 8))
comp_conv2d(conv2d, X).shape


输出结果

torch.Size([8, 8])


填充不同的高度和宽度,同时调整卷积核大小,使输入输出数据形状不变

conv2d = nn.Conv2d(1, 1, kernel_size=(5, 3), padding=(2, 1))
comp_conv2d(conv2d, X).shape


torch.Size([8, 8])


将高度和宽度步幅设为2(stride控制步幅)

conv2d = nn.Conv2d(1, 1, kernel_size=3, padding=1, stride=2)
comp_conv2d(conv2d, X).shape


torch.Size([4, 4])


一个稍微复杂的例子。

conv2d = nn.Conv2d(1, 1, kernel_size=(3, 5), padding=(0, 1), stride=(3, 4))
comp_conv2d(conv2d, X).shape


torch.Size([2, 2])

补充知识:

填充(上下边总填充量)一般取核边长-1

卷积步幅最好取1,一般取2,在计算量过大时取更大值

卷积核边长一般取奇数,因为padding=kernel-1,而padding是分在图片上下的,kernel为奇数,padding就可以对半分。





20 卷积层里的填充和步幅【动手学深度学习v2】的评论 (共 条)

分享到微博请遵守国家法律