为了账号安全,请及时绑定邮箱和手机立即绑定

Tensorflow CNN卷积的理解

标签:
深度学习

Tensorflow中的卷积函数

tf.nn.conv2d(input, filter, strides, padding, use_cudnn_on_gpu=None, name=None)

  • 第一个参数input:指需要做卷积的输入图像,它要求是一个Tensor,具有[batch, in_height, in_width, in_channels]这样的shape,具体含义是[训练时一个batch的图片数量, 图片高度, 图片宽度, 图像通道数],注意这是一个4维的Tensor,要求类型为float32和float64其中之一

  • 第二个参数filter:相当于CNN中的卷积核,它要求是一个Tensor,具有[filter_height, filter_width, in_channels, out_channels]这样的shape,具体含义是[卷积核的高度,卷积核的宽度,图像通道数,卷积核个数],要求类型与参数input相同,有一个地方需要注意,第三维in_channels,就是参数input的第四维

  • 第三个参数strides:卷积时在图像每一维的步长,这是一个一维的向量,长度4

  • 第四个参数padding:string类型的量,只能是"SAME","VALID"其中之一,这个值决定了不同的卷积方式(后面会介绍)

  • 第五个参数:use_cudnn_on_gpu:bool类型,是否使用cudnn加速,默认为true

  • 第六个参数:name参数用以指定该操作的name

  • 返回:Tensor,这个输出,就是我们常说的feature map,shape仍然是[batch, height, width, channels]这种形式。

CNN中卷积的理解

这篇文章对CNN卷积的介绍较为详细, https://buptldy.github.io/2016/10/01/2016-10-01-im2col/

文中的两个图比较直观,图二中,input features,可以理解为一个3x3图片的3通道数据,卷积核为2x2大小三通道 2个卷积核。单通道的图片数据转化为矩阵时,是按照卷积核的大小展开为一维向量。图一的理解,则需要交换input和kernel的位置,output map逆时针旋转90度。

webp

图一

webp

图二

实践

用tensorflow的conv2d来验证图2的数据,其关键是输入和filter的数据的构造。

filter的维数[2, 2, 3, 2], 2x2维,3通道,2个卷积核,构造出的数据,不能直接按照卷积核的原始数据reshape得道,而是要重新排列,排列顺序如图。如果要到如图中第一个卷积核的数据则用filter_arg[:, :, 0, 0](也可见代码中的注释部分,通过直接赋值构建filter的值)。同理可以构造输入图片的数据,最后执行的结果和图中一致。

webp

数据构建

import numpy as npimport tensorflow as tf

input_arg = tf.constant([
    [[1, 0, 1], [2, 2, 2], [0, 1, 1]],
    [[1, 0, 0], [1, 3, 1], [3, 2, 3]],
    [[0, 1, 3], [2, 1, 3], [2, 0, 2]]], dtype = tf.float32)# [filter_height, filter_width, in_channels, out_channels]#filter_arg = np.array(np.arange(24)).astype("float32")#filter_arg = np.reshape(filter_arg, [2, 2, 3, 2]).astype("float32")#filter_arg[:, :, 0, 0] =  [[1, 1], [2, 2]]#filter_arg[:, :, 1, 0] =  [[1, 1], [1, 1]] #filter_arg[:, :, 2, 0] =  [[0, 1], [1, 0]]#filter_arg[:, :, 0, 1] =  [[1, 0], [0, 1]]#filter_arg[:, :, 1, 1] =  [[2, 1], [2, 1]] #filter_arg[:, :, 2, 1] =  [[1, 2], [2, 0]] filter_arg = tf.constant([
    [[[1, 1],
    [1, 2],
    [0, 1]],

    [[1, 0],
    [1, 1],
    [1, 2]]],

    [[[2, 0],
    [1, 2],
    [1, 2]],

    [[2, 1],
    [1, 1],
    [0, 0]]]], dtype = tf.float32)

input_arg_normal = tf.reshape(input_arg, [1, 3, 3, 3])
filter_arg_normal = tf.reshape(filter_arg, [2, 2, 3, 2])
op1 = tf.squeeze(tf.nn.conv2d(input_arg_normal, filter_arg_normal, strides=[1,1,1,1], use_cudnn_on_gpu=False, padding='VALID'))with tf.Session() as sess:
    sess.run(tf.global_variables_initializer())
    input_out = sess.run(input_arg_normal)
    print(input_out.shape)
    print(input_out)
    print("*" * 20)
    filter_out = sess.run(filter_arg_normal)
    print(filter_out.shape)
    print(filter_out)
    print("*" * 20)
    print(sess.run(op1))

运行结果

(1, 3, 3, 3)[[[[1. 0. 1.]
   [2. 2. 2.]
   [0. 1. 1.]]  [[1. 0. 0.]
   [1. 3. 1.]
    [0, 1]],   [3. 2. 3.]]  [[0. 1. 3.]
   [2. 1. 3.]
   [2. 0. 2.]]]]
********************
(2, 2, 3, 2)[[[[1. 1.]
   [1. 2.]
   [0. 1.]]  [[1. 0.]
   [1. 1.]
   [1. 2.]]] [[[2. 0.]
   [1. 2.]
   [1. 2.]]  [[2. 1.]
   [1. 1.]
   [0. 0.]]]]
********************[[[14. 12.]
  [20. 24.]] [[15. 17.]
  [24. 26.]]]

参考文章

http://cs231n.github.io/convolutional-networks/

webp

经典卷积计算图



作者:YANWeichuan
链接:https://www.jianshu.com/p/a1790d5f5770


点击查看更多内容
TA 点赞

若觉得本文不错,就分享一下吧!

评论

作者其他优质文章

正在加载中
  • 推荐
  • 评论
  • 收藏
  • 共同学习,写下你的评论
感谢您的支持,我会继续努力的~
扫码打赏,你说多少就多少
赞赏金额会直接到老师账户
支付方式
打开微信扫一扫,即可进行扫码打赏哦
今天注册有机会得

100积分直接送

付费专栏免费学

大额优惠券免费领

立即参与 放弃机会
意见反馈 帮助中心 APP下载
官方微信

举报

0/150
提交
取消