小白必看:10步学会从零使用Keras框架

今天针对小白分享一篇使用 Keras 的终极指南,教大家通过 10 步掌握用 Keras 和 Python 搭建深度学习模型,包括设置开发环境、安装 Keras、加载数据集到定义模型、训练模型和评估模型等一整个流程。
本文并非一篇关于深度学习的深度教程,相反是教你如何以最快的速度用 Keras 从零搭建一个卷积神经网络,一共分为 10 步。在跟着本文一步步操作时,如果想深入了解某个功能和模块,打开 Keras 文档(keras.io/zh/)作为参考会比较有帮助。
内容步骤
10 步用 Keras 创建 CNN 模型:

  1. 设置开发环境
  2. 安装 Keras
  3. 导入库和模块
  4. 加载数据集
  5. 为 Keras 预处理输入数据
  6. 为 Keras 预处理类标签
  7. 定义模型架构
  8. 编译模型
  9. 用训练数据拟合模型
  10. 用测试数据评估模型

第 1 步:设置你的开发环境
在你的电脑上安装以下软件:

  • Python 2.7+ 或 Python 3
  • SciPy 和 Numpy
  • Matplotlib
  • Theano

强烈建议通过 Anaconda Distribution(continuum.io/downloads)安装Python、Numpy、Scipy 和 matplotlib,Anaconda 自带了这些包。
注:也可以用 TensorFlow(替换 Theano),不过为了简单起见,我们这里使用了 Theano。主要区别是再把数据输入到网络之前需要略微重塑数据。
安装后可以检查是否已正确安装了所有环境依赖:
打开命令行程序,输入:

$ python

你会看到 Python 解释器:

Python 2.7.12 |Anaconda 4.0.0 (x86_64)| (default, Jul  2 2016, 17:43:17)

接着,你可以导入你的库,打印它们的版本:

>>> import numpy
>>> import theano
>>> print numpy.__version__
1.11.0
>>> print theano.__version__
0.8.2
>>> quit()

第 2 步:安装 Keras
如果你是用的 Anaconda 安装,你会发现已经安装好了一个很棒的包管理系统,叫做 pip。
可以在命令行中输入 $ pip 来检查是否已安装,应该打印出一列命令和选项。如果没有安装 pip,可以到官网下载:
pip.pypa.io/en/stable/i
有了 pip 后,安装 Keras 就是小菜一碟了:

$ pip install keras$

可以确认是否已正确安装:

$ python -c "import keras; print keras.__version__"
Using Theano backend.
1.0.4

如果 Keras 版本过时了,升级新版也很容易:

$ pip install --upgrade keras
...
$ python -c "import keras; print keras.__version__"
Using Theano backend.
1.1.1

很好,我们现在启动一个新的 Python 文件,命名为 keras_cnn_example.py
第 3 步:导入库和模块
我们首先导入 Numpy,为电脑的伪随机数生成器设置一个种子数,这能让我们复现脚本中的结果:

import numpy as np
np.random.seed(123)  # for reproducibility

接着我们导入 Keras 中的序列模型类型,基本上是神经网络层的线性堆栈,非常适合我们本文要搭建的卷积神经网络。

from keras.models import Sequential

然后我们导入 Keras 中的“核心”层,这些层几乎在所有神经网络中都会用到:

from keras.layers import Dense, Dropout, Activation, Flatten

紧接着我们从 Keras 中导入 CNN 层,它们都是卷积层,能帮我们高效低用图像数据训练模型:

fromf  keras.layers import Convolution2D, MaxPooling2D

最后,我们导入一些实体程序,它们在后面会帮我们转换数据:

fromf  keras.utils import np_utils

现在我们有了搭建神经网络架构所需的一切材料。
第 4 步:从 MNIST 中加载图像数据
从零开始入门深度学习和计算机视觉,MNIST 会是个很不错的数据集。它足够我们训练和测试一个神经网络,而又能在个人电脑上易于管理。
Keras 库中已经包含了 MNIST 数据集,我们可以这样将它加载:

from keras.datasets import mnist
# 将MNIST 数据加载为训练集和测试集
(X_train, y_train), (X_test, y_test) = mnist.load_data()

看看数据集的形状:

print X_train.shape
# (60000, 28, 28)

很好,看起来我们的训练集中有 6 万个样本,每张图像大小为 28 x 28 像素。我们可以通过用 matplotlib 绘制第一个样本来确认一下:

from matplotlib import pyplot as plt
plt.imshow(X_train[0])

图像输出如下:

总体上看,在处理计算机视觉问题时,在做任何算法相关工作之前,以可视化的方式绘制数据会很有帮助,能够帮我们避免一些错误,比如错误解释了数据维度。
第 5 步:为 Keras 预处理输入数据
在使用 Theano 后端时,你必须为输入图像的深度明确地声明一个维度。例如,一张有 3 个 RGB 通道的全彩照片,深度会为 3.
我们的 MNIST 图像只有 1 个深度,但我们必须明确声明这一点。
换句话说,我们想将数据集的形状从[n,宽,高]转换为[n,深,宽,高]。
通过以下方式,我们可以很容易地做到:

X_train = X_train.reshape(X_train.shape[0], 1, 28, 28)
X_test = X_test.reshape(X_test.shape[0], 1, 28, 28)

可以再次打印 X_train 的维度进行确认:

print X_train.shape
# (60000, 1, 28, 28)

输入数据的最后预处理步骤就是将数据类型转换为 float 型数据 32 位,将数据值正则化为 [0,1] 范围内。

X_train = X_train.astype('float32')
X_test = X_test.astype('float32')
X_train /= 255
X_test /= 255

现在,我们的输入数据已经可以用于模型训练了。
第 6 步:为 Keras 预处理类标签
接着,我们看看类标签数据的形状:

print y_train.shape
# (60000,)

看着有点问题,我们应该有 10 个不同的类,每个对应一个数字,但我们目前只有一个单维数组。我们瞧瞧前 10 个训练样本的标签:

print y_train[:10]
# [5 0 4 1 9 2 1 3 1 4]

但有个问题。Y_train 和 y_test 数据没有分割成 10 个不同的类标签,而是表示为只有类值的单个数组。
我们可以很容易地修正这个问题:

Y_train = np_utils.to_categorical(y_train, 10)
Y_test = np_utils.to_categorical(y_test, 10)

现在我们再看看数据:

print Y_train.shape
# (60000, 10)

好多了!
第 7 步:定义模型架构
现在,我们开始定义模型架构。在实际工作中,研究人员会花费相当长的时间来研究模型架构。
因为本文主要是面向小白,所以这里不再深入讨论其中的理论和数学原理。这是个相当深的领域,建议通过一些专业课程来学习。
我们首先声明一个序列模型格式:

model = Sequential()

接着,声明输入层:

model.add(Convolution2D(32, 3, 3, activation='relu', input_shape=(1,28,28)))

输入形状参数应该为 1 个样本的形状,在这个情况下,还是(1,28,28),对应每张数字照片的形状(深,宽,高)。
但前 3 个参数表示的是什么?它们分别对应的是要使用的卷积过滤器的数量、每个卷积内核中的行数、每个卷积内核中的列数。
注:默认步幅大小为(1,1),可以通过‘subsample’参数进行调整。
我们通过打印当前模型输出的形状来进行确认:

print model.output_shape
# (None, 32, 26, 26)

接着我们只需向模型中添加更多的层即可,就跟组装乐高玩具一样:

model.add(Convolution2D(32, 3, 3, activation='relu'))
model.add(MaxPooling2D(pool_size=(2,2)))
model.add(Dropout(0.25))

虽然我们不会深入讲解,但我们刚才添加的 Dropout 层还是非常重要的,值得一提。 Dropout 是一种方法能正则化我们的模型,防止出现过拟合。
MaxPooling2D 是一种减少模型中参数的方法,方式是在之前的层上滑动一个 2×2 的池化过滤器,在 2×2 过滤器中取 4 个值的最大值。
到了这里,我们已经添加了 2 个卷积层。为了让模型的架构更完整,我们还需要添加一个全连接层和一个输出层。

model.add(Flatten())
model.add(Dense(128, activation='relu'))
model.add(Dropout(0.5))
model.add(Dense(10, activation='softmax'))

对于致密层(或全连接层),第一个参数时该层的输出大小。Keras 会自动处理层与层之间的连接。
注意,最后一层的输出大小为 10,对应了数字的 10 个类别。
同时也要注意到,卷积层的权重在传入全连接层之前必须扁平化(成为一维)。
整个模型架构如下所示:

model = Sequential()
model.add(Convolution2D(32, 3, 3, activation='relu', input_shape=(1,28,28)))
model.add(Convolution2D(32, 3, 3, activation='relu'))
model.add(MaxPooling2D(pool_size=(2,2)))
model.add(Dropout(0.25))
model.add(Flatten())
model.add(Dense(128, activation='relu'))
model.add(Dropout(0.5))
model.add(Dense(10, activation='softmax'))

现在我们需要做的就是定义损失函数和优化器,然后训练模型。
第 8 步:编译模型
现在我们终于到了最后阶段!最困难的部分已经过去了。
现在只需编译模型,就可以训练它了。在我们编译模型时,会声明损失函数和优化器(SGD,Adam 等等)。

model.compile(loss='categorical_crossentropy',
              optimizer='adam',
              metrics=['accuracy'])

Keras 有很多种损失函数以及“开箱即用”的优化器供我们使用。
第 9 步:用训练数据拟合模型
要想拟合模型,我们只需声明训练模型时的批次大小和周期数量,然后传入我们的训练数据。

model.fit(X_train, Y_train,
          batch_size=32, nb_epoch=10, verbose=1)
# Epoch 1/10
# 7744/60000 [==>...........................] - ETA: 96s - loss: 0.5806 - acc: 0.8164

很容易的对吧?
你还可以使用很多种回调函数来设置 Early Stopping 的规则,顺便保存模型权重或记录每个训练周期的历史数据。
第 10 步:用测试数据评估模型
最后,我们用测试数据评估搭建的模型:

score = model.evaluate(X_test, Y_test, verbose=0)

恭喜!到了这里,你已经做到了用 Keras 从零搭建一个深度学习模型。
下面是我们本文项目的全部代码:

# 3. 导入库和模型
import numpy as np
np.random.seed(123)  # for reproducibility
from keras.models import Sequential
from keras.layers import Dense, Dropout, Activation, Flatten
from keras.layers import Convolution2D, MaxPooling2D
from keras.utils import np_utils
from keras.datasets import mnist
# 4. 将MNIST数据加载为训练集和测试集
(X_train, y_train), (X_test, y_test) = mnist.load_data()
# 5. 预处理输入数据
X_train = X_train.reshape(X_train.shape[0], 1, 28, 28)
X_test = X_test.reshape(X_test.shape[0], 1, 28, 28)
X_train = X_train.astype('float32')
X_test = X_test.astype('float32')
X_train /= 255
X_test /= 255
# 6. 预处理类标签
Y_train = np_utils.to_categorical(y_train, 10)
Y_test = np_utils.to_categorical(y_test, 10)
# 7. 定义模型架构
model = Sequential()
model.add(Convolution2D(32, 3, 3, activation='relu', input_shape=(1,28,28)))
model.add(Convolution2D(32, 3, 3, activation='relu'))
model.add(MaxPooling2D(pool_size=(2,2)))
model.add(Dropout(0.25))
model.add(Flatten())
model.add(Dense(128, activation='relu'))
model.add(Dropout(0.5))
model.add(Dense(10, activation='softmax'))
# 8. 编译模型
model.compile(loss='categorical_crossentropy',
              optimizer='adam',
              metrics=['accuracy'])
# 9. 用训练数据拟合模型
model.fit(X_train, Y_train,
          batch_size=32, nb_epoch=10, verbose=1)
# 10. 用测试数据评估模型
score = model.evaluate(X_test, Y_test, verbose=0)

最后,再分享一个 Keras 速查表,方便大家学习:
s3.amazonaws.com/assets

发表评论

电子邮件地址不会被公开。 必填项已用*标注