在我前面的文章[火炉炼 AI] 深度学习 005 - 简单几行 keras 代码解决二分类问题 https://www.jianshu.com/p/09b5a5d82eec 中, 介绍了用 Keras 解决二分类问题. 那么多分类问题该怎么解决? 有哪些不同?
1. 准备数据集
为了演示, 本次选用了博文 keras 系列︱图像多分类训练与利用 bottleneck features 进行微调 (三) 中提到的数据集, 原始的数据集将所有类别的 train 照片放到 train 文件夹中, 所有的 test 照片放在 test 文件夹中, 而用不同数字开头来表示不同类别, 比如以 3 开头的照片就是 bus 类等. 首先将这些不同类别的照片放在不同的文件夹中, 最终的 train 文件夹有 5 个子文件夹, 每个子文件夹中有 80 张图片, 最终的 test 文件夹中有 5 个子文件夹, 每个子文件夹中有 20 张图片. 总共只有 500 张图片.
在代码上, 需要用 ImageDataGenerator 来做数据增强, 并且用 flow_from_directory 来从文件夹中产生数据流.
代码和二分类的文章基本相同, 此处就不贴出来了, 可以去我的 GitHub https://github.com/RayDean/DeepLearning 直接看全部的代码.
唯一的不同之处是要设置 class_mode='categorical', 而不是原来二分类问题的 class_mode='binary'
2. 模型的构建和训练
基本和二分类一样, 如下为模型的构建部分:
- # 4, 建立 Keras 模型: 模型的建立主要包括模型的搭建, 模型的配置
- from keras.models import Sequential
- from keras.layers import Conv2D, MaxPooling2D
- from keras.layers import Activation, Dropout, Flatten, Dense
- from keras import optimizers
- def build_model(input_shape):
- # 模型的搭建: 此处构建三个 CNN 层 + 2 个全连接层的结构
- model = Sequential()
- model.add(Conv2D(32, (3, 3), input_shape=input_shape))
- model.add(Activation('relu'))
- model.add(MaxPooling2D(pool_size=(2, 2)))
- model.add(Conv2D(32, (3, 3)))
- model.add(Activation('relu'))
- model.add(MaxPooling2D(pool_size=(2, 2)))
- model.add(Conv2D(64, (3, 3)))
- model.add(Activation('relu'))
- model.add(MaxPooling2D(pool_size=(2, 2)))
- model.add(Flatten())
- model.add(Dense(64))
- model.add(Activation('relu'))
- model.add(Dropout(0.5)) # Dropout 防止过拟合
- model.add(Dense(class_num)) # 此处多分类问题, 用 Dense(class_num)
- model.add(Activation('softmax')) #多分类问题用 softmax 作为 activation function
- # 模型的配置
- model.compile(loss='categorical_crossentropy', # 定义模型的 loss func,optimizer,
- optimizer=optimizers.RMSprop(), # 使用默认的 lr=0.001
- metrics=['accuracy'])# 主要优化 accuracy
- return model # 返回构建好的模型
改变之处是: 最后的 Dense 层需要用 Dense(class_num)来代替 Dense(1), 然后用多分类的标配 activation function: softmax. 在模型的配置方面, 也需要将 loss function 改为'categorical_crossentropy'.
通过模型的训练后, 最终结果如下所示:
从结果上看: 没有出现过拟合现象, 但是 test acc 不太稳定, 变化比较大. 在平台期后的 test acc 约为 0.85.
######################## 小 ********** 结 ###############################
1, 多分类问题和二分类问题基本相同, 不同之处在于: 1, 设置 flow_flow_directory 时要用设置 class_mode='categorical'.2, 模型的最后一层要用 Dense(class_num)和 softmax 这个多分类专用激活函数. 3, 模型的 loss function 要使用 categorical_crossentropy.
#################################################################
注: 本部分代码已经全部上传到 (我的 GitHub https://github.com/RayDean/DeepLearning ) 上, 欢迎下载.
来源: https://juejin.im/post/5bed169c6fb9a049f153c3fc