在Tensorboard的mnist示例中生成了意外的层

时间:2018-01-31 15:15:44

标签: python tensorflow deep-learning conv-neural-network tensorboard

为了学习张量流,我执行了这个tensorflow官方mnist脚本(cnn_mnist.py)并显示了带有张量板的图形。

以下是代码的一部分。 该网络包含两个转换层和两个密集层。

conv1 = tf.layers.conv2d(inputs=input_layer,filters=32,kernel_size=[5, 5],
      padding="same",activation=tf.nn.relu)

pool1 = tf.layers.max_pooling2d(inputs=conv1, pool_size=[2, 2], strides=2)

conv2 = tf.layers.conv2d(inputs=pool1,filters=64,kernel_size=[5, 5],
      padding="same",activation=tf.nn.relu)

pool2 = tf.layers.max_pooling2d(inputs=conv2, pool_size=[2, 2], strides=2)

pool2_flat = tf.reshape(pool2, [-1, 7 * 7 * 64])

dense = tf.layers.dense(inputs=pool2_flat, units=1024, activation=tf.nn.relu)

dropout = tf.layers.dropout(
      inputs=dense, rate=0.4, training=mode == tf.estimator.ModeKeys.TRAIN)

logits = tf.layers.dense(inputs=dropout, units=10)

然而,查看由张量板生成的图形,有三个转换层和三个密集层。 我没想到会生成conv2d_1dense_1

为什么生成了conv2d_1dense_1

mnist graph picture generated by tensorboard

2 个答案:

答案 0 :(得分:1)

这是一个很好的问题,因为它为# php garbage collection for file-based sessions on debian is done via # cronjob but roundcubemail uses mysql as storage during runtime which is # not cleaned up by the cronjob. So reenable the default php gc method php_admin_value session.gc_probability 1 <ifModule mod_rewrite.c> RewriteEngine On RewriteCond %{REQUEST_URI} ^/(roundcubemail|webmail) RewriteRule ^[a-zA-Z0-9]{16}/(.*) /%1/$1 [PT,L] </ifModule> <ifModule mod_authz_core.c> Require all granted </ifModule> <ifModule !mod_authz_core.c> Order Allow,Deny Allow from All </ifModule> 包装器的内部结构提供了一些启示。我们进行两个实验:

  • 完全按照问题运行模型。
  • 通过tf.layers参数向图层添加显式名称,然后重新运行。

没有图层名称的图表

这与你的图形相同,但我扩展并放大到logits密集层。请注意,name包含图层变量(内核和偏差),dense_1包含ops(矩阵乘法和加法)。

这意味着仍然是一层,但两个命名范围 - dense_2dense_1。这是因为这是第二个密集层,第一个已使用命名范围dense_2。变量创建与实际层逻辑分离 - 有densebuild方法, - 它们都尝试获取范围的唯一名称。这导致calldense_1分别保留变量和操作。

graph-1

指定名称的图表

现在让我们将dense_2添加到同一层并再次运行:

name='logits'

graph-2

你可以看到仍然有2个变量和2个操作,但是该层设法获取范围的一个唯一名称(logits = tf.layers.dense(inputs=dropout, units=10, name='logits') )并将所有内容放入其中。

结论

这是一个很好的例子,为什么张量流中的显式命名是有益的,无论它是关于张量直接还是更高层次。当模型使用有意义的名称而不是自动生成的名称时,会产生更少的混淆。

答案 1 :(得分:0)

它们只是tf.layers.conv2d中发生的变量创建和其他隐藏操作,而不仅仅是卷积操作本身(tf.nn.conv2d)和激活(同样适用于密集层)。只有2个卷积发生:正如您所看到的,如果您按照图表中的数据操作,它永远不会通过conv2D_1dense_1,只是这些操作的结果(基本上是所需的变量)对于卷积运算本身也作为输入给出。我实际上更惊讶的是没有看到同样出现在conv_2d上的东西,但我真的不担心!