34

深度学习中的反卷积(Transposed Convolution)

 3 years ago
source link: http://www.banbeichadexiaojiubei.com/index.php/2020/10/07/深度学习中的反卷积transposed-convolution/
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.
neoserver,ios ssh client

反卷积(Transposed Convolution)是一种图像上采样(UpSample)的方法,在DCGAN中用它来将随机采样的值转换为一张完整的图像。

d213d746-b80b-4bb2-ba9e-a493e75bf61c.gifDCGAN生成手写数字。图片来源【5】

Transposed Convolution

反向卷积也叫转置卷积,它是一种特殊的正向卷积,先按照一定的比例通过补0来扩大输入图像的尺寸,接着旋转卷积核(Kernel),再进行正向卷积。

反卷积的操作只是恢复了矩阵的尺寸大小,并不能恢复每个元素值。

tf.nn.conv2d_transpose(
    input, filters, output_shape, strides, padding='SAME', data_format='NHWC',
    dilations=None, name=None
)

Transposed Convolution将Output Size恢复为Input Size,对于Convolution过程,我们知道其Output Size与Input Size的尺寸关系如下:

$$

o=\left\lfloor \frac{i+2p-k}{s} \right\rfloor + 1

$$

其中,o为Output Size, i是Input Size, p为Padding Size,s为Stride。

若要将o恢复为i,需考虑2种情况,$\frac{i+2p−k}{s}$整除以及不整除两种情况。

详细的公式就不推导了,网上有很多资料,有兴趣可以深入研究下这些材料:

https://www.cnblogs.com/shine-lee/p/11559825.html

A guide to convolution arithmetic for deep learning

Tensorflow中实现反卷积

假设我们令输入图像为:

$$

\text{input} =

\begin{bmatrix}

1 & 2 & 3 \

4 & 5 & 6 \

7 & 8 & 9

\end{bmatrix}

$$

卷积核(kernel)为:

$$

\text{kernel} =

\begin{bmatrix}

1 & 0 & 0 \

0 & 1 & 0 \

0 & 0 & 1

\end{bmatrix}

$$

Case 1

如果要使输出的尺寸是5 x 5,步长stride = 2,tensorflow代码:

tf.nn.conv2d_transpose(
    value=input, filter=kernel,
    output_shape=[1,5,5,1], 
    strides=2, padding='SAME')

Tensorflow的内部做了以下几件事情:

1)根据步数stride对Input进行填充,即在Input的每个元素之间填充0 ,填充0的个数n与stride的关系为:

$$

\text{n} = \text{stride} – 1

$$

这里stride=1,所以在每个元素之间填充一个0。

$$

\text {input}_{pad}=\left[\begin{array}{ccccc}

0 & 0 & 0 & 0 & 0 & 0 & 0 \

0 & 1 & 0 & 2 & 0 & 3 & 0 \

0 & 0 & 0 & 0 & 0 & 0 & 0 \

0 & 4 & 0 & 5 & 0 & 6 & 0 \

0 & 0 & 0 & 0 & 0 & 0 & 0 \

0 & 7 & 0 & 8 & 0 & 9 & 0 \

0 & 0 & 0 & 0 & 0 & 0 & 0

\end{array}\right]

$$

2)用卷积核kernel对填充后的输入$input_{pad}$进行stride=1的正向卷积,输入尺寸为5 x 5。

$$

\text {output}=\left[\begin{array}{ccccc}

1 & 0 & 2 & 0 & 3 \

0 & 6 & 0 & 8 & 0 \

4 & 0 & 5 & 0 & 6 \

0 & 12 & 0 & 14 & 0 \

7 & 0 & 8 & 0 & 9

\end{array}\right]

$$

Case 2

如果要使输出的尺寸是6×6,其它参数不变,tensorflow代码:

tf.nn.conv2d_transpose(
    value=input, filter=kernel,
    output_shape=[1,6,6,1], 
    strides=2, padding='SAME')

卷积类型是same,我们首先在外围填充一圈0。此时仍然不能生成尺寸为6×6的图片,Tensorflow会在左上再填充一行和一列0,填充后的输入为:

$$

\text {input}=\left[\begin{array}{ccccccc}

0 & 0 & 0 & 0 & 0 & 0 & 0 & 0 \

0 & 0 & 0 & 0 & 0 & 0 & 0 & 0 \

0 & 0 & 1 & 0 & 2 & 0 & 3 & 0 \

0 & 0 & 0 & 0 & 0 & 0 & 0 & 0 \

0 & 0 & 4 & 0 & 5 & 0 & 6 & 0 \

0 & 0 & 0 & 0 & 0 & 0 & 0 & 0 \

0 & 0 & 7 & 0 & 8 & 0 & 9 & 0 \

0 & 0 & 0 & 0 & 0 & 0 & 0 & 0

\end{array}\right]

$$

对input执行卷积核为3×3的卷积操作,结果如下:

$$

\text {input}=\left[\begin{array}{cccccc}

1 & 0 & 2 & 0 & 3 & 0 \

0 & 1 & 0 & 2 & 0 & 3 \

4 & 0 & 6 & 0 & 8 & 0 \

0 & 4 & 0 & 5 & 0 & 6 \

7 & 0 & 12 & 0 & 14 & 0 \

0 & 7 & 0 & 8 & 0 & 9

\end{array}\right]

$$

反卷积动图效果

cce82649-d8c6-4920-9528-8119274be988.gifNo padding, no strides, transposed,图片来源【1】6ef0d3ec-853c-4684-b50a-c7c2160441a4.gifNo padding, strides=1, transposed,图片来源【1】

参考材料

1.https://github.com/vdumoulin/conv_arithmetic

2.https://www.tensorflow.org/api_docs/python/tf/nn/conv2d_transpose

3.https://zhuanlan.zhihu.com/p/31988761

4.https://www.cnblogs.com/shine-lee/p/11559825.html

5.https://www.tensorflow.org/tutorials/generative/dcgan?hl=zh-cn


About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK