zoukankan      html  css  js  c++  java
  • tensorflow处理mnist(一)

    这个文章是对google官方教程的解释

    预备知识

    [egin{equation*} left[ egin{array}{cccc} a_1 & a_2 & a_3 end{array} ight] end{equation*} ]

    [egin{equation*} softmax(a)= left[ egin{array}{cccc} frac{e^{a_1}}{e^{a_1}+e^{a_2}+e^{a_3}} & frac{e^{a_2}}{e^{a_1}+e^{a_2}+e^{a_3}} & frac{e^{a_3}}{e^{a_1}+e^{a_2}+e^{a_3}} end{array} ight] end{equation*} ]

    tensorflow里面有softmax的函数.可以直接调用.

    import tensorflow as tf
    a = tf.constant([.0, .0, .0, .0], tf.float32)
    b = tf.constant([1., 2., 3., 4.], tf.float32)
    result1 = tf.nn.softmax(a)
    result2 = tf.nn.softmax(b)
    sess = tf.Session()
    print(sess.run(result1))
    print(sess.run(result2))
    

    模型训练

    mnist = input_data.read_data_sets(r"D:mnistzip", one_hot=True)
    

    把mnist数据集读取内存.读入方法的细节放在以后讨论.这里只有注意one_hot=True这个参数.one_hot表示用非零即1的数组保存图片表示的数值.比如一个图片上写的是0,内存中不是直接存一个0,而是存一个数组[1,0,0,0,0,0,0,0,0,0].一个图片上面写的是1,那个保存的就是[0,1,0,0,0,0,0,0,0,0]

    x = tf.placeholder(tf.float32, [None, 784])
    W = tf.Variable(tf.zeros([784, 10]))
    b = tf.Variable(tf.zeros([10]))
    y = tf.matmul(x, W) + b
    

    构造一个模型.为了说明问题方便,假定数据集中只有16张照片(这个假设在后面的内容中一直存在).那么y的最终结果是一个16*10的矩阵,每一行代表一张图片.

    y_ = tf.placeholder(tf.float32, [None, 10])
    

    定义一个占位符,用于图片上的数.上面已经介绍过,一个图片上面写的是1,那么保存的就是[0,1,0,0,0,0,0,0,0,0]. 如果现在有16张图片,y_就是一个16*10的矩阵.

    cross_entropy = tf.reduce_mean(-tf.reduce_sum(y_ /* tf.log(tf.nn.softmax(y)), reduction_indices=[1]))
    

    reduction_indices是已经过时的参数,现在已经改成了axis,所以这个代码改为

    cross_entropy = tf.reduce_mean(-tf.reduce_sum(y_ /* tf.log(tf.nn.softmax(y)), axis=1))
    

    上面已经说过y是一个16*10的矩阵,tf.nn.softmax(y)也是一个16*10的矩阵.只不过y的每一行被归一化到[0,1]之间.tf.log(tf.nn.softmax(y))是取自然对数,不影响结构.y_是16*10的矩阵,tf.log(tf.nn.softmax(y))也是16*10的矩阵,y_*tf.log(tf.nn.softmax(y))是把2个矩阵的对应项相乘.这一步起到的作用是把不是照片上数字的概率清0,这时候结果还是16*10的矩阵.tf.reduce_sum(y_ * tf.log(tf.nn.softmax(y)), axis=1)是把各列的值相加形成一个新的矩阵.这时候结果变成1维数组,长度是16.里面的值是分类正确的概率.因为这是正确的概率,希望正确的概率越大越好,但是梯度下降算法一般时求某个变量的极小值.所以前面要加一个负号.这是一种直观但不严谨的解释,更精度的解释见有关熵的概念.tf.reduce_mean作用是把数组各个元素加起来.我们希望cross_entropy越小越好,求cross_entropy的极小值要用到反向传播算法.算法原理要懂,细节tensorflow已经帮我们实现了.

    train_step = tf.train.GradientDescentOptimizer(0.5).minimize(cross_entropy)
    

    这句的含义是训练的过程是求cross_entropy的极小值,学习率是0.5.下面开始看训练的代码.

    batch_xs, batch_ys = mnist.train.next_batch(16)
    

    这行代码的含义是从数据集中随机取出16张照片.每次训练所有照片效果理论上应该是比较好的,但是这样很花费时间和空间.所以每次随机取出若干张.这就是所谓的随机梯度下降算法.有关随机梯度下降算法收敛的原理这里不再讨论.batch_xs是一个16*784的矩阵,是训练的数据,batch_ys是一个16*10的矩阵,是训练数据的标签.

    sess.run(train_step, feed_dict={x: batch_xs, y_: batch_ys})
    

    这行代码才是把实际数据放到x,y_中,以上面指定的模型和方法更新W和b的值,使损失函数不断减小.

    评价训练结果

    correct_prediction = tf.equal(tf.argmax(y, 1), tf.argmax(y_, 1))
    

    y,y_都是在后面才赋具体值的.为了描述方便.假设y是16*10的矩阵.y_是16*10的矩阵.tf.argmax(y, 1)返回的是一个长度为16的一维数组,里面是最大概率的索引.y_是16*10的矩阵.tf.argmax(y_, 1)返回的是一个长度为16的一维数组,里面是图片是是几的索引.tf.equal(tf.argmax(y, 1), tf.argmax(y_, 1))返回的是一个长度为16的bool型的数组.相等的话为True,不相等的话为False. True越多说明训练的结果越好.

    accuracy = tf.reduce_mean(tf.cast(correct_prediction, tf.float32))
    

    tf.cast(correct_prediction, tf.float32)是把bool型数组转化为float型,True转化为1.0, False转化为0.0.reduce_mean时求float型数组的平均值,即正确的个数与所有个数之比.这个数越大越好,等于1说明100%分类正确.

    sess.run(accuracy, feed_dict={x: mnist.test.images, y_: mnist.test.labels})
    

    feed_dict={x: mnist.test.images, y_: mnist.test.labels}是把实际的数据放到x,y_中.

  • 相关阅读:
    metasploit 常用命令汇总
    MSF命令 收集
    【转载】虫师『性能测试』文章大汇总
    渗透测试、取证、安全和黑客的热门链接
    Hackers top in China
    国外整理的一套在线渗透测试资源合集[转载]
    Filezilla中文字符文件看不到或显示乱码的解决办法
    Filezilla 多目录的访问设置
    ISAPI在IIS7上的配置
    数据库主体在该数据库中拥有 架构,无法删除解决方法(转)
  • 原文地址:https://www.cnblogs.com/zhouyang209117/p/6517684.html
Copyright © 2011-2022 走看看