TensorFlow中conv2d中padding方式解释

tf1.9版本以上的conv2d函数存在8个输入参数,但是前4个是各种版本中都一直存在的参数,他们是进行卷积计算的重要的输入参数。input为输入的tensor,filter为滤波器的尺寸,strides为滑动距离表示,padding为边缘的处理机制('VALID'和‘SAME’)。

 本文着重介绍不同的padding方式,对输出的数据维度的影响。

常规的计算卷积的输入输出的维度变化的公式为:OUT = (IN-F+2*P)/S+1

VALID:边缘处理时,如果边缘不够一个kernel,会将其丢掉,计算公式为OUT=ceil((IN-F+1)/S)向上取整

SAME:边缘处理时,会增加补0的操作,使边缘能满足一个kernel,计算公式为OUT=ceil(IN/S)向上取整

比如下面的示例代码:

import tensorflow as tf

def conv2d_test():
    inp = tf.Variable(tf.random_normal([1,7,7,5]))
    f = tf.Variable(tf.random_normal([3,3,5,1]))
    op = tf.nn.conv2d(inp,f,strides=[1,3,3,1],padding='VALID')
    
    with tf.Session() as sess:
        sess.run(tf.initialize_all_variables())
        print(sess.run(op).shape)


if __name__ == '__main__':
    conv2d_test()   

根据VALID公式计算,结果应该为ceil(7-3+1)/3 = 2。运行结果为(1, 2, 2, 1)

下面看padding为SAME的形式:

import tensorflow as tf

def conv2d_test():
    inp = tf.Variable(tf.random_normal([1,7,7,5]))
    f = tf.Variable(tf.random_normal([3,3,5,1]))
    op = tf.nn.conv2d(inp,f,strides=[1,3,3,1],padding='SAME')
    
    with tf.Session() as sess:
        sess.run(tf.initialize_all_variables())
        print(sess.run(op).shape)


if __name__ == '__main__':
    conv2d_test()  

根据SAME公式计算,结果应该为ceil (7/3) = 3。运行结果为(1, 3, 3, 1)

这样计算的时候公式还得按照方式不同使用不同的公式,所以是否可以按照一个公式计算,我们考虑常规公式的计算,此时不考虑padding,计算公式为out =(in -F)/ S +1,我们带入上述公式(7-3)/3 +1 = 2.33,所以如果为VALID,结果向下取整;如果为SAME,向上取整(经验公式)。

PS:一般情况下,如果设计网络时为了保证输入输出的数据维度保证不变,一般选择步长为1,padding为‘SAME’。

猜你喜欢

转载自blog.csdn.net/legend_hua/article/details/81180461