1.3 MNIST数据集介绍

这里使用由手写数字及其标签组成的图像集MNIST(经美国国家标准与技术研究所修改)。自从1999年发布以来,这个经典数据集被用于基准分类算法。

数据文件train.csv和test.csv由从0到9的手写数字灰度图像组成。一个数字图像是一个数学函数:f(x,y)=像素值。图像是二维的。

我们可以在图像上执行数学函数,通过计算图像上的梯度变化来测量像素值变化的速度和方向。为了识别图像,将图像转换为只有一个颜色通道的简单灰度图。图像的RGB表示是由三个颜色通道组成的:红色、蓝色和绿色。在RGB配色方案中,图像是由红色、蓝色和绿色三种图像叠加而成的。在灰度配色方案中,颜色并不重要。彩色图像在计算和分析上都更难,因为它们会占据更多的内存空间。亮度是图像明度和暗度的度量,对于识别物体非常有用。例如在自动驾驶汽车应用中检测车道线时,颜色就很重要,因为必须区分黄线和白线,而灰度图不能提供足够的信息来区分黄线和白线。

计算机将任何灰度图解释为一个矩阵,矩阵的每个元素都是一个像素。每个图像都是28×28的像素矩阵,总共有784个像素。每个像素都有一个对应的像素值,该值表示特定像素的明度或暗度。像素值取0~255范围内的整数,其中0表示最暗,255表示最白,灰色像素在0到255之间。

最简单的人工神经网络

一个简单的两层神经网络如图1-5所示。

图1-5 两层神经网络

第一层是输入层,最后一层是输出层,中间层是隐含层。如果隐含层不止一个,则这样的网络就是深度神经网络。

隐含层中每个神经元的输入和输出都与下一层中每个神经元相连。根据问题的不同,每一层的神经元个数都是任意的。让我们看一个例子,你可能已经知道这个简单的例子,就是手写数字识别,用于从图像中检测数字,比如说5。网络将接收一个标签为5的图像并输出1或0,1表示图像确实是5,而0表示不是。一旦网络创建好,就必须进行训练。我们可以用随机权重初始化网络,然后输入被称为训练数据集的样本。对每个输入样本,我们检查输出,计算误差率,然后调整权重,直到当输入标签为5的图像时,网络输出1,而其他都输出0。这种类型的训练方法称为监督学习,而调整权重的方法称为反向传播。在构建人工神经网络模型时,一个主要考虑的问题是如何为隐含层和输出层选择激活函数。三个最常用的激活函数是sigmoid函数、双曲正切函数和ReLU。sigmoid的美妙之处在于它在z点的导数就是简单的z乘以1-z,这意味着:

dy/dx=σ(x)(1-σ(x))

这有助于我们以一种方便的方式有效地计算神经网络中的梯度。如果给定层的逻辑函数的前馈激活函数都保存在内存中,那么可以通过简单的乘法和减法来评估特定层的梯度,而不是实现并重新评估sigmoid函数,因为这需要额外的求幂运算。图1-6展示了ReLU激活函数,当x<0时,函数值为0,当x>0时,线性斜率是1。

图1-6 ReLU激活函数

ReLU是一个非线性函数,计算函数是f(x)=max(0,x),即如果输入是负值,ReLU函数值为0,如果输入x>0,ReLU函数值为x。这意味着激活函数在0处被阈值化(请参见图1-6左边部分)。TensorFlow在tf.nn.relu()中实现了ReLU函数:

反向传播是误差反向传播的简称,是训练人工神经网络的常用方法,常与优化方法(如梯度下降)结合使用。反向传播在计算梯度中的损失函数时会考虑网络中的所有权重。该优化方法采用梯度法进行权重更新以优化损失函数。

运用TensorFlow创建一个单层神经网络

让我们运用TensorFlow一步步建立一个单层神经网络。本例主要基于MNIST数据集。该数据集是一组28×28像素的手写数字灰度图像,包含55 000个训练数据、10 000个测试数据和5 000个验证数据。每个MNIST数据点有两部分:一个手写数字图像和一个对应标签。加载数据的代码块如下所示。one_hot=True意味着标签是one-hot编码向量,而不是实际数字。例如,如果标签是2,你会看到[0,0,1,0,0,0,0,0,0,0],这样就可以直接在网络输出层使用它:

设置占位符和变量的代码如下:

下面在TensorFlow中设置优化器:

在开始训练之前,先构建变量初始化运算,然后构建测量预测准确率的运算,如下所示:

现在开始训练模型,如以下代码片段所示: