机器学习的“hello world”

承接上篇 “信我,就一句话解释神经网络” ,接下来与大家分享机器学习世界里的“hello,world”

背景:

MNIST是一个手写数字的数据库,该数据库分为两部分:手写的图片及其对应的标签数字。在上一篇文章提到了,对于普通程序来说,很难定义“猫”。当然,图片数字没有瞄那么困难。因为至少数字不会有不同的形态和种类。大体数字仍然要满足一定的规律及形态。但是,由于是手写的,书写习惯及书写位子不同,仍然给数字识别带来困难。接下来我们将以机器学习的方法来识别该数据库。

数据整理:

MNIST是一个简单的手写数字的数据库,如下图所示。同时MNIST 也包含了数字标签,告诉我们每张图片对应的数字,5,0,4,1。 那么X就是每张图片,y就是图片对应的真实数字。

训练样本X:

MNIST数据库包含了60000个手写数字及其对应的标签。单一手写数字图片是28*28像素,如下图所示。

对于该图片,我们的处理方式是将[28,28]的图片拉平变成[784,1]的向量,换句话说此图片有784个特征值或者说是784维向量空间。

最终整个训练样本X就变成了[55000,784]的矩阵。

训练样本Y:

样本数据库的标签是[5,0,4,1]。需要将其转换为‘One-hot Vector’,如下图分别代表着5,0,4,1. 此向量只有一个维度值为1,其他均为0.

例如对于数字5的向量是[0,0,0,0,0,1,0,0,0,0].

大家可能对于y为什么要变成[0,0,0,0,0,0,0,1,0,0] 这种形式。 我个人理解是:如果仍然使用(0~9)作为y值,那么没有办法有效分配 概率区间。比如[0,0,0,0,0,0,0,1,0,0] 这种形式只要计算每个元素的概率就行,各元素之间不会相互影响。但是对于(0~9):如果y_预测 算出来是0.5那么怎么划分,如果算出来是-10000呢? 所以原来的y会受本身的数字属性影响。

神经网络结构:

神经网络输出层:

我们面对的问题是,输入一张图片需要判断对应的数字。该问题可以转化为一个概率问题,输入一张图片后,需要能够计算出对应到10个选项的概率(0~9)。比如,模型输入一张图片后,可能判断80%是9, 5%是8,剩余的数字都有一些非常小的概率。

Softmax就是处理该问题的模型。Softmax能够计算每个选项的概率,并且汇总概率为100%;

例如:在训练前,图片数字7,对应的Y_实际与 Y_预测

从概率上来说,Y_实际 代表的是100%概率是7

从概率上来说,Y_预测 代表的是每个数字的概率都是10%

Y_实际 = [0,0,0,0,0,0,0,0,1,0,0]

Y_预测 = [0.1,0.1,0.1,0.1,0.1,0.1,0.1,0.1,0.1,0.1]

强调下:在训练前,输出层输出的数值并不重要,重要的是形式与Y_实际 一致

神经网络输入层:

神经网络输入层是由输入对象决定的。因为MNIST的图片有784个像素,所以输入层有784的神经元。

隐藏层:

此次隐藏层为,全连接(Dense)层,每个神经元都与上一层及下一层的神经元相互连接。

至于神经元的作用已经在上一篇 “信我,就一句话解释神经网络” 提到。神经网络隐藏层由于各个神经元相互连接,矩阵运算。使得其本身已经成为一个特别复杂的公式。

但是其本质是一个公式,该公式的输出会受各个神经元参数的影响。

损失与训练:

我们都已经知道:损失,其实指的是神经网络输出层结果与 实际数字标签的差异。而训练的目的就是缩小该差异。

那么就MNIST来说,Y_预测与 Y_实际的差异是神经网络预测的概率与样本对应概率的差异。神经网络在训练前,有一个最基本的要求需要满足,即神经网络输出层的格式需要与实际数字标签的格式一致,如下:

Y_实际 = [0 , 0,0,0,0,0,0,0,1,0,0]

Y_预测 = [0.1,0.1,0.1,0.1,0.1,0.1,0.1,0.1,0.1,0.1]

在训练结束后,以下是输入数字图片7,对应的神经网络预测结果。大家能看到在第八个位子上(由于是0开始)的概率是99.67%

[0.000000754 0.000001885 0.000337282 0.002868271 0.000000039 0.000015610 0.000000001 0.996765610 0.000003079 0.000007443]

所以神经网络训练的目的就是缩小差异,缩小预测的概率与实际概率的差距。

训练:

那么训练是如何实现的呢?(Gradient Descent 基础版逻辑)

神经网络搭建好之后,当输入一张图片后,神经网络输出结果其实取决于神经网络的参数。所以,假设损失与 参数的关系如下图:

那么训练的过程其实就是一个下山的过程。首先,找到切线;然后向下走一小步。

反向传递(Backpropagation),看神经网络的资料必然会遇到这个单次,反向传递。通俗的理解,其实就是在我们训练之初,存在很大差异。我们通过找该差异区间的切线,调整了神经网络参数,使得差异值在切线方向下降一小步(下山)

下图是训练60000个样本,4轮之后的差异值。

训练结果:

最终该神经网络的准确率达到97%,最后给大家展示下该神经网络预测错误的几个例子:

大家能看出来,实际上预测不准确的基本都是写的并不规范的例子。比如第二个图。

承接之前一篇 “信我,就一句话解释神经网络”,神经网络就是一个巨复杂的公式。如果要训练该公式达到分类(MNIST本质上是把图片分成10类,那么首先需要考虑到Y的形式,搭建整个神经网络。然后将Y_预测 与 Y_实际的 GAP定义为损失值。 再根据样本进行训练。

本质上,该神经网络最终是根据输入的784个像素,计算出在【10,1】10维向量的概率分布。该概率分布计算的准确程度取决于几个因素: 样本数量是否足够及离散、神经网络结构及激励函数、损失函数的定义及优化方程的定义 。

代码实践:

这么复杂的东西。怎么猜也得几百行代码吧。

最惊喜的地方就在这里,整个神经网络结构搭建(除初始数据整理,训练及画图)真的只要10行代码,,,就10行。意不意外,惊不惊喜。

  • 发表于:
  • 原文链接:https://kuaibao.qq.com/s/20180619A1LJBZ00?refer=cp_1026
  • 腾讯「云+社区」是腾讯内容开放平台帐号(企鹅号)传播渠道之一,根据《腾讯内容开放平台服务协议》转载发布内容。

同媒体快讯

扫码关注云+社区

领取腾讯云代金券