如何解释CNN中的model.summary()输出?

时间:2020-04-06 13:17:10

标签: tensorflow keras deep-learning google-colaboratory cnn

我是深度学习和CNN的新手。如果已创建CNN(如屏幕截图所示),那么如何解释model.summary()所描述的输出。我无法理解不同图层的输出形状。

模型摘要:

Model: "sequential_3"
_________________________________________________________________
Layer (type)                 Output Shape              Param #   
=================================================================
conv2d_14 (Conv2D)           (None, 29, 29, 32)        1568      
_________________________________________________________________
max_pooling2d_6 (MaxPooling2 (None, 14, 14, 32)        0         
_________________________________________________________________
conv2d_15 (Conv2D)           (None, 11, 11, 32)        16416     
_________________________________________________________________
max_pooling2d_7 (MaxPooling2 (None, 5, 5, 32)          0         
_________________________________________________________________
flatten_3 (Flatten)          (None, 800)               0         
_________________________________________________________________
dense_6 (Dense)              (None, 32)                25632     
_________________________________________________________________
dense_7 (Dense)              (None, 10)                330       
=================================================================
Total params: 43,946
Trainable params: 43,946
Non-trainable params: 0

neural network design

3 个答案:

答案 0 :(得分:2)

根据问题,假设每个图像的大小为(32, 32, 3)

然后,Keras附加了一个额外的维度,用于处理多个批次,即在单个时期的每个步骤中训练多个图像。由于批次大小可以变化,因此其大小用无来表示。因此,输入形状变为(None, 32, 32, 3)

使用(32, 32)过滤器对(4, 4)图像进行卷积处理,步幅和膨胀率为1,并使用“有效”填充来生成(32 - 4 + 1, 32 - 4 + 1) = (29, 29)大小的输出。由于您有32个此类过滤器,因此输出形状变为(29, 29, 32)

默认的MaxPooling内核的形状为(2, 2),步幅为(2, 2)。将其应用于(29, 29)图像会得到形状为(((29 - 2)//2) + 1, ((29 - 2)//2) + 1)) = (14, 14)的图像。

此模式可以扩展到所有Conv2D和MaxPooling层。

Flatten层沿所有通道获取所有像素,并创建一维矢量(不考虑批处理大小)。因此,将(5, 5, 32)的输入展平为(5 * 5 * 32) = 800的值。

参数计数

Conv2D层的参数数量由以下公式给出:

(内核高度*内核宽度* input_channels * output_channels)+(如果使用偏置,则为output_channels)。

因此,对于具有3个输入通道,32个输出通道且内核大小为(4, 4)的第一个Conv2D层,参数的数量为(4 * 4 * 3 * 32) + 32 = 1568

答案 1 :(得分:0)

您的第一层是卷积,其卷积形状未知(您已经知道,您可以在input_shape= ...处定义卷积。

第一个卷积具有形状为(None, 29, 29, 32)的输出,其中:

  • None是批次大小
  • 29和29是生成的图像的大小
  • 32是该卷积的滤波器数量,也是其输出中的通道数量

然后您有一个maxpooling层,它将卷积的输出作为输入。池的输出形状为(None, 14, 14, 32),因此它将图像的大小除以2,其余部分保持原样。

然后,您有另一个卷积,以池的输出作为输入,此新卷积的输出形状为(None, 11, 11, 32)。您在这里也使用了32个过滤器。

... .....

....

然后您有一个Flatten层,该层将图像转换为单个矢量,输出形状为(None, 800),其中None仍是未更改的批量大小,即800是输入张量中的所有元素,现在在单个向量中,批次中每个样本一个向量。

然后是Dense层,第一层包含32个单位,第二层包含10个单位。

模型的最终输出形状为(None, 10)。批次中每个样本输出10个值。


每个层都有许多参数(通常是权重)。可训练的参数将通过反向传播进行更新。不可训练的参数将保持静态或将使用其他方法更新(只有BatchNormalization之类的几层具有使用不同方法更新的参数)

您的模型共有43946重量,均可训练。

答案 2 :(得分:0)

对于Conv2d, 如您所见,输出形状为(None,10,10,64)。第一个维度表示批次大小,目前为“无”。因为网络事先不知道批次大小。拟合数据后,将不会用拟合数据时给出的批量大小来代替。

Input shape

4D tensor with shape: (batch, channels, rows, cols) if data_format is "channels_first" 
or 4D tensor with shape: (batch, rows, cols, channels) if data_format is 
"channels_last".

Output shape

4D tensor with shape: (batch, filters, new_rows, new_cols) if data_format is 
"channels_first" or 4D tensor with shape: (batch, new_rows, new_cols, filters) if 
data_format is "channels_last". rows and cols values might have changed due to 
padding.

对于 maxpool2d 层,其值与上述相同,但略有变化,如下所示。

**Input**

If data_format='channels_last': 4D tensor with shape: (batch_size, rows, cols, channels)
If data_format='channels_first': 4D tensor with shape: (batch_size, channels, rows, cols)

**Output**

If data_format='channels_last': 4D tensor with shape: (batch_size, pooled_rows, pooled_cols, channels)
If data_format='channels_first': 4D tensor with shape: (batch_size, channels, pooled_rows, pooled_cols)

现在,我们可以简单地在另一个卷积层的顶部添加一个卷积层,因为卷积的输出维与输入维相同。 我们通常在卷积层的顶部添加Dense层以对图像进行分类。但是,将数据输入到形状(batch_size,单位)的密集层2D数组中。卷积层的输出是4D数组。因此,我们必须将从卷积层接收的输出的尺寸更改为2D数组。

我们可以通过在卷积层之上插入一个Flatten层来做到这一点。展平层将图像的3维压缩为一个维。现在,我们只有形状为(batch_size, squashed_size),的2D数组,这对于密集层是可以接受的。

希望这会对您有所帮助。