• 卷积神经网络CNN


    padding 有时候容易迷糊,这里汇总一下

    卷积中的 padding

    当取 SAME 时,原则上保持输入和输出尺寸相同但这只是在 步长为1时 如此

    总结来说,

    n 表示 输入尺寸

    f 表示 卷积核尺寸

    s 表示 步长

    p 表示 padding 的尺寸

    out 表示 输出尺寸

    p = (f - 1) / 2

    out = (n + 2p - f + 1) / s 向上取整

    也可以这么 out = (n + 2p - f) / s + 1 向下取整

    变换一下,out = (n + 2p - f) / s + 1 = (n + f -1 - f) / s + 1 = (n - 1) / s + 1 向下取整,不好记

    这么变换,out = (n + 2p - f + 1) / s = (n + f - 1 - f + 1) / s = n / s 向上取整

    当取 VALID 时

    VALID 原则就一条,不填充,就是正常滑动,滑完是多少就是多少,

    公式就简单了 out = (n - f + 1) / s 向上取整

    池化中的 padding

    当取 SAME 时,也会填充,但不是保持尺寸不变,而是当 池化野 滑到边界时,如果边界剩余尺寸小于池化野,则填充至一样大,否则不填充

    当取 VALID 时,不填充

    公式好像和 卷积 一样

    另外,

    卷积核尺寸最好是奇数,更容易找到卷积锚点

    池化的步长最好大于1,这样才能起到降维作用

    示例

    x = tf.Variable(np.random.randint(1, 3, size=(1, 5, 5, 3)), dtype=tf.float32)
    
    
    ##### 卷积
    w = tf.Variable(np.random.uniform(0, 1, size=(3, 3, 3, 4)), dtype=tf.float32)
    w2 = tf.Variable(np.random.uniform(0, 1, size=(2, 2, 3, 4)), dtype=tf.float32)  # size 为偶数
    w3 = tf.Variable(np.random.uniform(0, 1, size=(4, 4, 3, 4)), dtype=tf.float32)  # size 为偶数
    
    ### padding = SAME
    # stride = 1
    y1 = tf.nn.conv2d(x, w, strides=(1, 1, 1, 1), padding='SAME')     # p=(3-1)/2=1 (5+2*1-3+1)/1=5
    print(y1.shape)     # (1, 5, 5, 4)
    y12 = tf.nn.conv2d(x, w2, strides=(1, 1, 1, 1), padding='SAME')   # p=(2-1)/2=0.5 不向上取整 (5+2*0.5-2+1)/1=5
    print(y12.shape)     # (1, 5, 5, 4)
    # strider != 1
    y2 = tf.nn.conv2d(x, w, strides=(1, 2, 2, 1), padding='SAME')     # p同上 (5+2*1-3+1)/2=2.5 向上取整3
    print(y2.shape)     # (1, 3, 3, 4)
    y22 = tf.nn.conv2d(x, w2, strides=(1, 2, 2, 1), padding='SAME')   # p同上 (5+2*0.5-2+1)/2=2.5 向上取整3
    print(y22.shape)     # (1, 3, 3, 4)
    
    ### padding = VALID
    # stride = 1
    y3 = tf.nn.conv2d(x, w, strides=(1, 1, 1, 1), padding='VALID')      # (5-3+1)/1=3
    print(y3.shape)     # (1, 3, 3, 4)
    y32 = tf.nn.conv2d(x, w2, strides=(1, 1, 1, 1), padding='VALID')      # (5-2+1)/1=4
    print(y32.shape)     # (1, 4, 4, 4)
    # strider != 1
    y4 = tf.nn.conv2d(x, w, strides=(1, 2, 2, 1), padding='VALID')      # (5-3+1)/2=1.5 向上取整2
    print(y4.shape)     # (1, 2, 2, 4)
    y42 = tf.nn.conv2d(x, w2, strides=(1, 2, 2, 1), padding='VALID')      # (5-2+1)/2=2  此时有列信息被忽略了
    print(y42.shape)     # (1, 2, 2, 4)
    
    
    ##### 池化
    w = [1, 3, 3, 1]
    
    ### padding = SAME
    # stride = 1
    y5 = tf.nn.max_pool(x, w, strides=(1, 1, 1, 1), padding='SAME')    # 5/1=5
    print(y5.shape)     # (1, 5, 5, 3)
    # strider != 1
    y6 = tf.nn.max_pool(x, w, strides=(1, 2, 2, 1), padding='SAME')     # 5/2=2.5 向上取整3
    print(y6.shape)     # (1, 3, 3, 3)
    
    ### padding = VALID
    # stride = 1
    y7 = tf.nn.max_pool(x, w, strides=(1, 1, 1, 1), padding='VALID')    # (5-3+1)/1=3
    print(y7.shape)     # (1, 3, 3, 3)
    # strider != 1
    y8 = tf.nn.max_pool(x, w, strides=(1, 2, 2, 1), padding='VALID')    # (5-3+1)/2=1.5 向上取整2
    print(y8.shape)     # (1, 2, 2, 3)

    参考资料:

    https://www.cnblogs.com/CK85/p/10287142.html  最简单直接

    https://zhuanlan.zhihu.com/p/77471866 

    https://cloud.tencent.com/developer/article/1080155

    https://zhuanlan.zhihu.com/p/74159232

    https://zhuanlan.zhihu.com/p/46744988

  • 相关阅读:
    HorizontalScrollView水平滚动控件的使用
    ScrollView垂直滚动控件的使用
    RatingBar评分控件的使用
    ProgressBar进度条的使用
    AnalogClock和DigitalClock时间和日期控件
    DatePicker输入日期控件的使用
    ImageView从网络上获取图像
    CentOS 7.3 安装配置Samba服务器
    python元组内置函数
    Python元组
  • 原文地址:https://www.cnblogs.com/yanshw/p/15497984.html
Copyright © 2020-2023  润新知