Keras用法教程:深入学习深度学习

2021年11月28日06:23:49 发表评论 954 次浏览

深度学习是近年来广受欢迎的编程领域之一。越来越难找到一个不将这个新流行语用于某个目的的领域。

语音和图像识别。自然语言处理。大数据。所有这些领域都在深度学习的帮助下取得了重大突破。由于深度学习的力量,几年前还只是幻想的东西,例如自动驾驶汽车,现在几乎成为现实。

所以我们认为现在是开发人员进入这个领域的理想时机,即使你只是在试验。Keras 是 Python 中最强大的深度学习库之一,它使任何人都可以更轻松地利用这项技术,而无需担心复杂的基础理论。

如何使用Keras?在本教程中,我们将向你简要介绍深度学习,然后在不过多关注理论方面的情况下,直接进入使用 Keras 构建 DL 模型的过程,包括详细的深度学习实现示例。

正如你在本Keras用法教程末尾所发现的,Keras 即使对于初学者也非常容易。但是,如果你对简单的机器学习概念有所了解,那么我们在本教程中做出的某些决定对你来说会更有意义。


什么是深度学习?

深度学习是机器学习的一个子集。它模仿人脑及其神经网络的结构,使机器能够从原始数据中获取输出。

传统机器学习的主要缺点之一是特征提取。由于传统 ML 模型本身无法处理原始数据,因此我们必须在将数据传递给模型之前提取数据中的重要特征。

程序员需要对问题域有深入的了解,才能推导出应该提取哪些特征以及如何提取这些特征。更不用说,此过程中的人工干预为不捕获原始数据中重要的高级特征开辟了可能性。

但是深度学习消除了特征提取的需要。深度学习模型中的神经网络可以学习识别原始数据中的抽象和隐含模式,并自行映射它们对特定输出的影响。换句话说,DL 结合了特征提取和分类,并在单个模型中执行它们。

这使深度学习在理解原始数据中的隐藏模式和特征方面优于机器学习。因此,它们提供了优于 ML 模型的改进结果,尤其是随着数据集大小的增加。


典型神经网络的架构

神经网络小说案例,来源:oreilly.com
神经网络架构示例,来源:oreilly.com

DL 模型中的典型神经网络由多层组成。每个节点包含一组带有数值(例如 0.3、2.45)的节点。

两个相邻层中节点之间的连接由权重定义。它定义了前一个节点的值在决定下一个节点的值时的权重(例如 1.2、5)。换句话说,权重决定了一个节点在确定另一个节点的价值方面的影响。权重值是在训练神经网络期间计算的。

神经网络的第一层称为输入层。输入层的层数取决于输入向量的大小。如果输入向量的大小为 12,则输入层的大小也应为 12。

神经网络的最后一层是输出层。当模型执行分类任务时,输出层应该为每个可能的分类结果包含一个节点。

例如,如果使用 DL 模型来识别输入图像中显示的数字(从 0 到 9),则它在输出层中应该有 10 个节点。当模型对给定的输入图像进行预测时,每个输出节点都会给出图像中的数字是该节点所代表的数字的概率。然后将具有最高概率的数字视为模型的最终预测。

输入层和输出层之间的所有其他层都称为神经网络的隐藏层。这些连接其节点的层和权重执行数学运算以输出模型的最终预测。一个神经网络可以有多个隐藏层,这取决于它期望完成的任务。


什么是卷积神经网络 (CNN)?

由于我们将在本教程中使用 Keras 构建一个简单的 CNN,因此在继续之前,让我们尝试了解 CNN 与常规神经网络有何不同。

CNN 是一种将图像作为输入的神经网络。换句话说,当我们调整神经网络的属性时,特别是为了更好地处理图像输入及其内在质量,我们称之为 CNN。

因此,与常规神经网络相比,CNN 架构包括一些特定类型的层。卷积层、池化层和全连接层是少数这样的例子。

卷积层

卷积层应用过滤器,使用名为卷积的数学运算来汇总图像小区域内的特征 。例如,我们可以定义一个卷积层,其内核(将其视为一个窗口)大小为 3x3。它通过图像向量并在给定时间对内核中的 9 个元素应用卷积。然后该层根据卷积结果修改图像向量中的输入值。

检查此 giphy 以了解卷积层如何作用于图像。 https://giphy.com/gifs/blog-daniel-keypoints-i4NjAwytgIRDW

池化层

池化层用于通过删除其冗余数据来减小输入的大小。它使将输入图像中的特定特征映射到精确位置变得困难,从而提高了模型的灵活性。

池化将图像划分为一组不重叠的区域,并通过简单的操作(例如查找值的最大值、最小值或平均值)将它们的值池化为一个值。最大池化是最常用的池化技术类型。

最大池化示例
最大池化示例

展平

扁平化层只是将一个多维向量扁平化为一个长的一维向量。如果你将一个 13x13 的向量传递给扁平化层,它会输出一个大小为 169 的长向量。

全连接层

全连接层结合了前一层中不同节点已识别的各个特征,以描绘关于输入的更大图景。因此,全连接中的每个节点都应该与其前一层中的每个节点相连。


Keras用法教程:什么是 Keras?

在本教程中,我们将使用 Keras 构建深度学习模型。Keras 是一个用 Python 编写的深度学习库。Keras 抽象了深度学习算法背后的复杂逻辑,并为初学者简化了新模型的构建。Keras 允许在实现过程中使用多个后端,包括 Tensorflow 和 Theano。

安装和设置 Keras

在安装 Keras 之前,你应该在系统上安装 Python(版本 3.6-3.8)和 pip。然后,只需运行以下命令即可开始安装。

pip install keras

KerasTensorflow 2 发行版捆绑在一起,你可以在其中将其导入为 tensorflow.keras。在这个实现中,使用的后端默认是 Tensorflow。

pip install tensorflow

要设置项目,我们只需从 Keras 导入 Numpy 和相关模块。

import numpy as np
from tensorflow.keras.models import Sequential
from tensorflow.keras.layers import Dense, Dropout, Activation, Flatten
from tensorflow.keras.layers import Convolution2D, MaxPooling2D
from tensorflow.keras.utils import to_categorical

如何使用Keras:加载数据集

在本教程中,我们使用 手写数字的MNIST 数据集。它包含 0-9 手写数字的 28x28 灰度图像。它的测试数据集包含 60000 张图像,而测试集包含 10000 张图像。

我们构建的 CNN 旨在将图像作为输入,并从 10 个可能的输出中预测它显示的数字。

由于 MNIST 数据集与 Keras 发行版捆绑在一起,因此我们可以直接加载它而无需任何额外工作。

from tensorflow.keras.datasets import mnist
(X_train, y_train), (X_test, y_test) = mnist.load_data()

load_data 函数加载训练和测试数据集。每个数据集包含一组图像(X_train,X_test)和一组它们显示的数字的标签(y_train,y_test)。

如果我们检查图像数据的形状:

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

此输出确认我们有 60000 张训练图像和 10000 张大小为 28x28 的测试图像。

我们还可以绘制图像以更好地了解数据集。

from matplotlib import pyplot as plt
plt.imshow(X_train[1])
数据集中的样本数字
数据集中的样本数字

Keras用法教程:预处理图像数据

在提供图像以训练和测试我们的深度学习模型之前,我们需要对图像进行归一化和重塑。

将图像像素值归一化为介于 0 和 1 之间,可以更轻松、更快速地训练模型。为了在不丢失数据的情况下进行规范化,首先,我们应该将它们的类型转换为 32 位浮点数。

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

我们用 Keras 构建的神经网络需要 3D 图像作为输入。由于这些 MNIST 图像是灰度图像,我们必须使用 expand_dims 方法专门添加深度为 1 的第三维。

X_train = np.expand_dims(X_train, axis=3)
X_test = np.expand_dims(X_test, axis=3)

如果我们在此重塑步骤后检查图像数据集的新形状:

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

我们可以看到图像现在如何具有新的三维。


深度学习实现示例:预处理图像标签

如果我们检查图像标签变量的形状:

print(y_train.shape) #(60000,)
print(y_test.shape) #(10000,)

可以看到测试和训练标签数据都存储为一维数组。

如果我们检查存储在其中一个数组中的值以获得更好的主意:

print(y_train[1]) #0

如你所见,这些标签数组直接存储了图像中的数字。但是我们的神经网络必须在输出层使用 10 个节点来识别每个数字。因此,我们必须对这些标签数据进行编码以使用十个类来表示每个数字。例如, 5 应编码为[0, 0, 0, 0, 0, 1, 0, 0, 0, 0].

Keras 提供了一种实用方法来轻松执行此任务。

y_train = to_categorical(y_train)
y_test = to_categorical(y_test)

现在,图像标签数据集的形状是:

print(y_train.shape) #(60000, 10)
print(y_test.shape) #(10000, 10)

如何使用Keras:是时候创建深度学习模型了

我们正在构建的模型将由 7 层组成,包括输入层和输出层。实际上,决定添加到网络的层的数量和类型取决于大量的实验、经验和大量的数学。

在本教程中,我们不会深入研究理论或花时间进行实验。相反,我们将采用构建 CNN 时常用的架构。

但是,你可以完全自由地调整此架构并尝试不同的层,以了解它们最终如何影响最终结果。

使用 Keras 构建模型时,我们必须使用Sequential 类或Model 类作为其基础。我们将要使用的 Sequential 类允许构建层的线性堆栈。让我们开始创建此类的实例。

model = Sequential()

我们添加到模型的第一层将充当输入层。而我们添加的输入层也是一个二维卷积层。

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

在这里,我们创建了一个卷积层,它使用 32 个 3x3 内核从输入中提取特征。它使用 ReLU 作为激活函数。

我们神经网络的下一层是池大小为 2x2 的池化层。

model.add(MaxPooling2D(pool_size=(2, 2)))

然后,我们向我们的模型添加另一个卷积层和一个池化层。额外的卷积层可以训练我们的模型识别图像中的高级特征,而额外的池化层提高了模型的灵活性。

model.add(Convolution2D(64, kernel_size=(3,3), activation="relu"))
model.add(MaxPooling2D(pool_size=(2, 2)))

下一步是使用展平层展平输入向量。

model.add(Flatten())

我们需要为我们的模型添加一个 dropout 层,以防止它过度拟合训练集。dropout 层故意忽略或“丢弃”先前节点的输出以逃避过度拟合。我们的 dropout 层接受 0.5 的 dropout 率。

model.add(Dropout(0.5))

最后,我们向神经网络添加一个全连接层作为输出层。它使用 softmax 激活函数来确定输出值。

model.add(Dense(10, activation='softmax'))

就是这样。我们的模型架构现已完成。在下面,你可以在一个地方看到模型的完整架构。

model = Sequential()

model.add(Convolution2D(32, kernel_size=(3,3), activation="relu", input_shape=(28, 28, 1)))
model.add(MaxPooling2D(pool_size=(2, 2)))

model.add(Convolution2D(64, kernel_size=(3,3), activation="relu"))
model.add(MaxPooling2D(pool_size=(2, 2)))

model.add(Flatten())
model.add(Dropout(0.5))

model.add(Dense(10, activation='softmax'))

我们可以使用以下函数查看模型的摘要。

model.summary()
Model: "sequential_4"
_________________________________________________________________
Layer (type)                 Output Shape              Param #
=================================================================
conv2d_7 (Conv2D)            (None, 26, 26, 32)        320
_________________________________________________________________
max_pooling2d_6 (MaxPooling2 (None, 13, 13, 32)        0
_________________________________________________________________
conv2d_8 (Conv2D)            (None, 11, 11, 64)        18496
_________________________________________________________________
max_pooling2d_7 (MaxPooling2 (None, 5, 5, 64)          0
_________________________________________________________________
flatten_4 (Flatten)          (None, 1600)              0
_________________________________________________________________
dropout_4 (Dropout)          (None, 1600)              0
_________________________________________________________________
dense_5 (Dense)              (None, 10)                16010
=================================================================
Total params: 34,826
Trainable params: 34,826
Non-trainable params: 0

Keras用法教程:编译和训练模型

在训练模型之前,我们应该通过传递优化函数(adam、SGD 等)、损失函数和评估指标来编译它。

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

现在,我们可以使用 Keras 拟合方法训练模型。它将在 10 个时期内进行训练,批量大小为 128。我们还使用 10% 的训练数据来验证模型。

model.fit(X_train, y_train, batch_size=128, epochs=10, validation_split=0.1)
Epoch 1/10
422/422 [==============================] - 21s 49ms/step - loss: 0.3711 - accuracy: 0.8857 - val_loss: 0.0863 - val_accuracy: 0.9770
Epoch 2/10
422/422 [==============================] - 22s 53ms/step - loss: 0.1151 - accuracy: 0.9651 - val_loss: 0.0564 - val_accuracy: 0.9840
Epoch 3/10
422/422 [==============================] - 24s 57ms/step - loss: 0.0852 - accuracy: 0.9740 - val_loss: 0.0487 - val_accuracy: 0.9873
Epoch 4/10
422/422 [==============================] - 23s 53ms/step - loss: 0.0735 - accuracy: 0.9779 - val_loss: 0.0428 - val_accuracy: 0.9893
Epoch 5/10
422/422 [==============================] - 23s 54ms/step - loss: 0.0642 - accuracy: 0.9799 - val_loss: 0.0418 - val_accuracy: 0.9885
Epoch 6/10
422/422 [==============================] - 23s 54ms/step - loss: 0.0577 - accuracy: 0.9823 - val_loss: 0.0374 - val_accuracy: 0.9898
Epoch 7/10
422/422 [==============================] - 26s 61ms/step - loss: 0.0538 - accuracy: 0.9831 - val_loss: 0.0354 - val_accuracy: 0.9907
Epoch 8/10
422/422 [==============================] - 23s 54ms/step - loss: 0.0485 - accuracy: 0.9852 - val_loss: 0.0375 - val_accuracy: 0.9897
Epoch 9/10
422/422 [==============================] - 22s 53ms/step - loss: 0.0468 - accuracy: 0.9852 - val_loss: 0.0344 - val_accuracy: 0.9908
Epoch 10/10
422/422 [==============================] - 25s 60ms/step - loss: 0.0434 - accuracy: 0.9865 - val_loss: 0.0304 - val_accuracy: 0.9912

那太容易了。现在我们有一个训练有素的深度学习模型,它在验证数据上显示出超过 99% 的准确率,可以识别手写数字的图像。


深度学习实现示例:评估模型

为了确认我们模型的准确性,我们可以使用我们的测试数据集对其进行评估。

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

现在,如果我们打印评估结果:

print("accuracy", score[1]) #accuracy 0.9894999861717224
print("loss", score[0]) #loss 0.028314810246229172

我们的模型在测试数据集上的准确率接近 99%。是不是很神奇?


使用经过训练的模型进行预测

如何使用Keras?最后,我们可以使用这个新训练的深度学习模型进行预测。让我们获取模型对测试数据集中前 20 张图像的预测,并根据原始图像标签查看结果。

predictions = model.predict(X_test[:20])
print("predictions:", np.argmax(predictions, axis=1))
print("labels     :", np.argmax(y_test[:20], axis=1))
predictions: [7 2 1 0 4 1 4 9 5 9 0 6 9 0 1 5 9 7 3 4]
labels     : [7 2 1 0 4 1 4 9 5 9 0 6 9 0 1 5 9 7 3 4]

我们的模型已经让所有这些都正确了!


Keras用法教程总结

今天,我们向你介绍了一个近年来在开发者社区非常流行的编程领域。尽管这是一个有很多数学理论的艰难领域,但 Keras 使神经网络的工作变得非常容易,即使对于完全的初学者也是如此。所以我希望这篇文章能让你继续尝试深度学习来构建有趣和有用的 AI 模型。

感谢你的阅读!

木子山

发表评论

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen: