卷积神经网络(CNN)
本教程演示如何训练一个简单的卷积神经网络(CNN)来对CIFAR图像进行分类。由于本教程使用Keras Sequential API,创建和训练我们的模型只需要几行代码。
下载并准备CIFAR10数据集
CIFAR10数据集包含10个类中的60000张彩色图像,每个类中有6000张图像。数据集分为50,000张训练图像和10,000张测试图像。这些类是互斥的,它们之间不存在重叠。
验证数据
为了验证数据集看起来是正确的,让我们绘制来自训练集的前25张图像,并在每张图像下面显示类名。
class_names < -c(“飞机”,“汽车”,“鸟”,“猫”,“鹿”,“狗”,“青蛙”,“马”,“船”,“卡车”)指数< -1:30.票面价值(mfcol =c(5,6),3月=代表(1,4),oma =代表(0.2,4))cifar$火车$x[…]索引% > %purrr::array_tree(1)% > %purrr::set_names(class_names [cifar$火车$y(指数)+1])% > %purrr::地图(as.rastermax =255)% > %purrr::我走(~{情节(方式);标题(.y)})
创建卷积基
下面的6行代码使用一个通用模式定义卷积基:Conv2D和MaxPooling2D层的堆栈。
作为输入,CNN接受形状的张量(image_height, image_width, color_channels),忽略批大小。如果您对这些维度不熟悉,那么color_channels指的是(R,G,B)。在本例中,您将配置我们的CNN来处理形状(32,32,3)的输入,这是CIFAR图像的格式。您可以通过传递参数来实现这一点input_shape
到第一层。
模型< -keras_model_sequential()% > %layer_conv_2d(过滤器=32,kernel_size =c(3.,3.),激活=“relu”,input_shape =c(32,32,3.))% > %layer_max_pooling_2d(pool_size =c(2,2))% > %layer_conv_2d(过滤器=64,kernel_size =c(3.,3.),激活=“relu”)% > %layer_max_pooling_2d(pool_size =c(2,2))% > %layer_conv_2d(过滤器=64,kernel_size =c(3.,3.),激活=“relu”)
让我们显示到目前为止模型的体系结构。
总结(模型)
# #模型:“顺序 " ## ___________________________________________________________________________ ## 输出层(类型)的形状参数 # ## =========================================================================== ## conv2d (conv2d)(没有,30、30、32)896 ## ___________________________________________________________________________ ## max_pooling2d (MaxPooling2D)(32)没有,15日,15日,0 ## ___________________________________________________________________________ ## conv2d_1 (Conv2D)(13, 13日,64) 18496 ## ___________________________________________________________________________ ## max_pooling2d_1 (MaxPooling2D)(没有6 64)0 ## ___________________________________________________________________________ ## conv2d_2 (Conv2D)(没有4 64)36928 ## =========================================================================== ## 总参数:56320 # #可训练的参数:56320 # # Non-trainable参数:0 ## ___________________________________________________________________________
在上面,你可以看到每个Conv2D和MaxPooling2D层的输出是一个形状的3D张量(高度,宽度,通道)。宽度和高度维度会随着你深入网络而缩小。每个Conv2D层的输出通道的数量由第一个参数控制(例如,32或64)。通常,随着宽度和高度的缩小,您可以(通过计算)在每个Conv2D层中添加更多的输出通道。
在顶部添加密集的层
为了完成我们的模型,您将把卷积基(形状(3,3,64))的最后一个输出张量输入到一个或多个密集层来进行分类。稠密层以向量作为输入(为1D),而当前的输出是一个3D张量。首先,您将3D输出平铺(或展开)为1D,然后在上面添加一个或多个密集层。CIFAR有10个输出类,因此您使用最后一个带有10个输出和一个softmax激活的密集层。
模型% > %layer_flatten()% > %layer_dense(单位=64,激活=“relu”)% > %layer_dense(单位=10,激活=“softmax”)
下面是我们模型的完整架构。
请注意Keras模型是可变的对象,您不需要在上面的chubnk中重新分配模型。
总结(模型)
# #模型:“顺序 " ## ___________________________________________________________________________ ## 输出层(类型)的形状参数 # ## =========================================================================== ## conv2d (conv2d)(没有,30、30、32)896 ## ___________________________________________________________________________ ## max_pooling2d (MaxPooling2D)(32)没有,15日,15日,0 ## ___________________________________________________________________________ ## conv2d_1 (Conv2D)(13, 13日,64) 18496 ## ___________________________________________________________________________ ## max_pooling2d_1 (MaxPooling2D)(没有6 64)0 ## ___________________________________________________________________________ ## conv2d_2 (Conv2D)(没有4 64)36928 ## ___________________________________________________________________________ ## 平(平)(没有,1024)0 ## ___________________________________________________________________________ ## 密度(密度)(没有,64) 65600 ## ___________________________________________________________________________ ## dense_1(致密)(没有,10)650 ## =========================================================================== ## 总参数:122570 # #可训练的参数:122570 # # Non-trainable参数:0 ## ___________________________________________________________________________
如您所见,我们的(3,3,64)输出在经过两个密集层之前被平展成形状为(576)的向量。
编译和训练模型
模型% > %编译(优化器=“亚当”,损失=“sparse_categorical_crossentropy”,指标=“准确性”)< -历史模型% > %适合(x =cifar$火车$x,y =cifar$火车$y,时代=10,validation_data =unname(cifar$测试),verbose =2)
# #火车在50000个样本,验证10000个样本33 # #时代1/10 # # 50000/50000 - s -损失:1.8909 -准确性:0.3912 - val_loss: 1.4419 - val_accuracy: 0.4769 # #时代2/10 # # 50000/50000 - 31 s -损失:1.3519 -准确性:0.5165 - val_loss: 1.3589 - val_accuracy: 0.5253 # #时代3/10 # # 50000/50000 - 32 s -损失:1.1962 -准确性:0.5797 - val_loss: 1.1695 - val_accuracy: 0.5867 # #时代4/10 # # 50000/50000 - 34 s -损失:1.0811 -准确性:0.6243 - val_loss: 1.1108 - val_accuracy:0.6217 # #时代5/10 # # 50000/50000 - 34 s -损失:1.0010 -准确性:0.6516 - val_loss: 1.0483 - val_accuracy: 0.6463 # #时代33 # # 50000/50000——6/10 s -损失:0.9441 -准确性:0.6725 - val_loss: 1.0655 - val_accuracy: 0.6376 # #时代33 # # 50000/50000——7/10 s -损失:0.8754 -准确性:0.6966 - val_loss: 1.0486 - val_accuracy: 0.6528 # #时代33 # # 50000/50000——8/10 s -损失:0.8300 -准确性:0.7127 - val_loss: 1.1089 - val_accuracy: 0.6313 # #时代33 # # 50000/50000——9/10 s -损失:0.7887 -精度:0.7246 - val_loss: 1.0807 - val_accuracy: 0.6439 ## Epoch 10/10 ## 50000/50000 - 34s - loss: 0.7503 - accuracy: 0.7398 - val_loss: 1.0982 - val_accuracy: 0.6576