我是靠谱客的博主 愤怒流沙,最近开发中收集的这篇文章主要介绍深入了解 反卷积,觉得挺不错的,现在分享给大家,希望可以做个参考。

概述

本来想写个叫做 深入理解反卷积,后来一想这不就跟写了“精通C++”一样嘛,就写个了解得了。等写完了发现,似乎啥也没写,想写的很多,但是无从下笔啊。。。

首先来看看mxnet和pytorch中的卷积和反卷积是怎么用的:

torch.nn.Conv2d(in_channels, out_channels, kernel_size, stride=1, padding=0, groups=1, bias=True)
torch.nn.ConvTranspose2d(in_channels, out_channels, kernel_size, stride=1, padding=0, output_padding=0, bias=True)
mxnet.gluon.nn.Conv2D(channels, kernel_size, strides=(1, 1), padding=(0, 0), dilation=(1, 1), groups=1, layout='NCHW', activation=None, use_bias=True, weight_initializer=None, bias_initializer='zeros', in_channels=0, **kwargs)
mxnet.gluon.nn.Conv2DTranspose(channels, kernel_size, strides=(1, 1), padding=(0, 0), output_padding=(0, 0), dilation=(1, 1), groups=1, layout='NCHW', activation=None, use_bias=True, weight_initializer=None, bias_initializer='zeros', in_channels=0, **kwargs)[source]

怎么说呢,参数基本上是一样的,但是mxnet的好处就是也可以不指定输入的channel,等到了第一次数据输入的时候再确定输入的通道数是多少。
借鉴其他文章的说法:

o = [ (i + 2p - k)/s ] +1 (1)
其中:
O : 为 output size
i: 为 input size
p: 为 padding size
k: 为kernel size
s: 为 stride size
[] 为下取整运算

这里有动画的演示:https://github.com/vdumoulin/conv_arithmetic
但是究竟是不是这样的呢,在pytorch源代码中我们可以看到:
pytorch/aten/src/THNN/generic/SpatialConvolutionMM.c(https://github.com/pytorch/pytorch/blob/04fe2453c450d51b3a611cdcd1e2661e1fdf2e44/aten/src/THNN/generic/SpatialConvolutionMM.c)
第54行:


int64_t outputHeight = div_rtn<int64_t>(exactInputHeight - kH, dH) + 1;
int64_t outputWidth
= div_rtn<int64_t>(exactInputWidth - kW, dW) + 1;

这里的padding工作在之前一步已经完成了,的确和上述的公式是对应的。

附上一些原理解释的链接:
https://blog.csdn.net/lanadeus/article/details/82534425(反卷积矩阵的讲解)

其实里面还有一个不起眼的参数:group,这里group的用法也比较奇怪:

inputs = torch.randn(1, 4, 5, 5)
weights = torch.randn(4, 2, 3, 3)
z = F.conv_transpose2d(inputs, weights, padding=0,groups =4)
print (z.shape)

这里实际上是pytorch的后端实现,再往下就是torch._C了就解析到了C语言源代码了,这里实际上已经是在做输入函数和该层参数的计算了,但是doc中写的是,权重的输出channel 的数值是 inputs/groups 这是啥意思呢?

其实groups的意思是将对应的输入通道与输出通道数进行分组, 默认值为1, 也就是说默认输出输入的所有通道各为一组。 比如输入数据大小为90x100x100x32,通道数32,要经过一个3x3x48的卷积,group默认是1,就是全连接的卷积层。

如果group是2,那么对应要将输入的32个通道分成2个16的通道,将输出的48个通道分成2个24的通道。对输出的2个24的通道,第一个24通道与输入的第一个16通道进行全卷积,第二个24通道与输入的第二个16通道进行全卷积。

极端情况下,输入输出通道数相同,比如为24,group大小也为24,那么每个输出卷积核,只与输入的对应的通道进行卷积。

这个思想最早来自于Alexnet,当时这么搞实际上是因为当时的显存有限,他弄了两块卡来计算,当时也没有更好的并行神经网络框架,于是就这么搞了,后来在另外的论文中,有人指出,这方法并不是很好用,于是后来大家就没有怎么关注这个参数了,都是默认1来全卷积。近来发现mxnet框架用反卷积做上采样,这样的话,group就必须和输入一致才可以了。

最后

以上就是愤怒流沙为你收集整理的深入了解 反卷积的全部内容,希望文章能够帮你解决深入了解 反卷积所遇到的程序开发问题。

如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。

本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
点赞(42)

评论列表共有 0 条评论

立即
投稿
返回
顶部