美文网首页
# tensorflow实战笔记(一)

# tensorflow实战笔记(一)

作者: Kean_L_C | 来源:发表于2017-11-02 00:09 被阅读492次

    获取数据

    from tensorflow.examples.tutorials.mnist import input_data
    
    mnist = input_data.read_data_sets(r'D:\PycharmProjects\HandWritingRecognition\TF\data',
                                      one_hot=True)  # 读取数据(如果是初次运行则需要下载)
    # 数据分为3部分:train, test, validation
    print(mnist.train.images.shape)  # 输入X的维度55000 x 784, 表示5w多训练样本,28*28的像素得到784个灰度,没有考虑结构关系
    print(mnist.train.labels.shape)  # 输出维度为55000 x10, 识别结果是0-9,维度为10;one-hot编码:向量的识别数字对应位子为1其他为0
    print(mnist.validation.images.shape)  # 5000 x 784
    print(mnist.test.images.shape)  # 10000 x 784
    

    softmax模型

    softmax回归模型解释

    212.PNG

    在上介绍后直接简化为下面(不支持latex,只能截图):

    捕获.PNG

    SGD训练模型
    过程中需要定义损失函数:交叉熵

    212.PNG
     # SGD
    sess = tf.InteractiveSession()  # 创建一个默认的交互session,不同的session里面的运算是独立的
    X = tf.placeholder(dtype=tf.float32, shape=[None, 784])  # feed数据占位,None直接取决于minibatch的数量,用None代替
    W = tf.Variable(initial_value=tf.zeros(shape=[10, 784]), name='W', dtype=tf.float32)  # 初始化权重变量
    b = tf.Variable(initial_value=tf.zeros(shape=[10]), name='b', dtype=tf.float32)
    y = tf.nn.softmax(tf.matmul(X, W, transpose_b=True) + b)  # 预测值
    y_ = tf.placeholder(dtype=tf.float32, shape=[None, 10])   # 真实值
    loss = tf.reduce_mean(-tf.reduce_sum(y_ * tf.log(y), reduction_indices=[1]))  # reducemean:对每个batch数据训练结果取平均
    train = tf.train.GradientDescentOptimizer(learning_rate=0.5).minimize(loss)  # 采用随机梯度下降法
    tf.global_variables_initializer().run()  # 所有参数初始化并,直接调用run方法, 前面采用的InteractiveSession,所以不需要sess.run
    for i in range(1000):
        # iteration:1000
        batch_x, batch_y = mnist.train.next_batch(100)  # size of batch:100
        train.run({X: batch_x, y_: batch_y})
    # 计算模型的准确率
    predres = tf.equal(tf.argmax(y, 1), tf.argmax(y_, 1))  # 找到两者的最大数值的位置,判断是否一致,返回bool型
    accuracy = tf.reduce_mean(tf.cast(predres, tf.float32))  # cast转化数据的类型
    print(accuracy.eval({X: mnist.test.images, y_: mnist.test.labels}))
    

    准确率:0.9183
    reduce_sum:reduction_indices=[1]理解为pandas的按行求和,minibatch数据求交叉熵得到100 x 10 的矩阵结果。

    自动编码

    212.PNG
    def xavier_init(in_num, out_num, const=1):
        """
        :param in_num: 
        :param out_num: 
        """
        value = const * np.sqrt(6 / (in_num + out_num))
        return tf.random_uniform(shape=(in_num, out_num), minval=-value, maxval=value, 
        dtype=tf.float32)
    
    • 类初始化定义
      一个隐藏层, n_input 输入信号个数784, n_hidden隐藏层节点数量, transfer信号函数, optimizer最优求解方法,scale利用高斯函数加入信号噪声的参数。
    class AdditiveGaussianNoiseAutoEncoder(object):
        def __init__(self, n_input, n_hidden, transfer=tf.nn.softplus,
                     optimizer=tf.train.AdamOptimizer(learning_rate=0.1), scale=0.01):
            self.n_input = n_input  # 输入节点数
            self.n_hidden = n_hidden  # 下一隐藏层层网络的节点数(仅仅考虑一个隐藏层)
            self.transfer = transfer  # 激活函数
            self.training_scale = scale  # 高斯噪声系数
            self.x = tf.placeholder(dtype=tf.float32, shape=[None, n_input])
            self.weight = self.__init_weight()
            # 计算隐藏层的输出信息号
            self.hidden = self.transfer(
                tf.add(
                    # 给输入信号加入高斯分布的噪声
                    tf.matmul(self.x + scale * tf.random_normal(shape=[n_input, ]),
                              self.weight['w1']), self.weight['b1']
                )
            )
            # 给将隐藏层的输出信号hadden复原
            self.reconstruction = tf.add(tf.matmul(self.hidden, self.weight['w2']),
                                         self.weight['b2']
                                         )
            # 计算复原信号与原来信号的差距:平方误差
            self.cost = 0.5 * tf.reduce_sum(tf.pow(tf.subtract(self.reconstruction, self.x), 2.0))
            self.optimizer = optimizer.minimize(self.cost)  # 优化损失函数
            init = tf.global_variables_initializer()
            self.sess = tf.Session()
            self.sess.run(init)
    
    • 权重初始化方法
      self.weight = self.__init_weight(), 类的初始化中我们用的代码,权重有两组一组,w1 b1与前面所讲到的softmax模型的矩阵运算一致,得到初始化权重和偏执的转置,但是w1调用了xavier函数。w2、b2则是用来对前面的过程的逆向操作(不是求矩阵的逆,仅仅代表流程:信息 -> hidden输出 -> +噪声 -> 还原成初始信号,类似于后面多了个隐藏层节点个数等于输入节点个数),得到在hidden的输出并加入高斯噪声,然后还原信号过程,次过程结果为reconstruction。cost是用二次损失函数来衡量还原后的信号和原始信号的误差程度。
        def __init_weight(self):
            weights = {}
            weights['w1'] = tf.Variable(xavier_init(self.n_input, self.n_hidden))
            weights['b1'] = tf.Variable(tf.zeros(shape=[self.n_hidden], dtype=tf.float32))
            weights['w2'] = tf.Variable(tf.zeros(shape=[self.n_hidden, self.n_input], dtype=tf.float32))
            weights['b2'] = tf.Variable(tf.zeros(shape=[self.n_input], dtype=tf.float32))
            return weights
    
    • 定义图节点调用函数
      前面在init中定义了所需要的一切,但是这仅仅都是图的节点,并不会执行,只有你在调用时候,才会执行,那么这个函数就是调用函数。(如果对图和节点困惑,就参考tensorflow的官网定义)
        def patial_fit(self, X):
            # X :batch数据
            # 执行损失cost和优化器的节点
            cost, opt = self.sess.run((self.cost, self.optimizer), feed_dict={self.x: X})
            return cost
    
    • 定义单独调用损失函数节点的函数
      这里主要为了用在测试数据上计算,信号还原的泛化能力
        def calc_total_cost(self, X):
            # 仅仅执行cost节点:自动编码完成后,用于训练数据评价模型
            return self.sess.run(self.cost, feed_dict={self.x: X})
    
    • 信号归一化处理调用sklearn模块函数和随机生成batch训练数据
    def standard(X_train, X_test):
        prep = preprocessing.StandardScaler().fit(X_train)
        X_train = prep.transform(X_train)
        X_test = prep.transform(X_test)
        return X_test, X_train
    
    def get_block(data, batch_size):
        start_index = np.random.randint(0, len(data) - batch_size)
        return data[start_index:(start_index + batch_size)]
    
    • 结果
      自动编码代码
      Epoch: 0001 cost= 418982712119.877807617
      Epoch: 0011 cost= 17215478609.007709503
      Epoch: 0021 cost= 23005525169.679157257
      Epoch: 0031 cost= 3799043043.911016464
      Epoch: 0041 cost= 37020387.181381851
      Epoch: 0051 cost= 390609961.420690894
      Epoch: 0061 cost= 68717674183.661369324
      Epoch: 0071 cost= 4283807699.044072151
      Epoch: 0081 cost= 428911581.832145751
      Epoch: 0091 cost= 10010243.328763649
      Total cost: 1.11217e+14

    多层感知机

    1. dropout 是一种bagging技术。
    2. 神经网络是一个非凸优化的问题,SGD经常会陷入局部最优解,局部最优解一般能得到比较好的分类效果,并且有时全局最优解的泛华能力并不好。
    3. 对于不同的学习速率结果有很大的变化,
    4. Adam:a method for stockastic optimization
    5. Adadelta: an adaptive learning rate method
    6. ReLU:解决梯度弥散(gradient vanishment)
      $$max(0, x)$$
      a. 单侧抑制
      b. 相对宽阔的兴奋区间
      c. 洗漱性的激活函数
    7. 优化器的介绍
    • tensorflow 实现
      前面已经接触过softmax来拟合输出,现在仅仅需要在前面的基础上加入中间一个隐藏层如下,矩阵的计算方式不变,随着?的加入。那么权重的初始也会发生变化。这里需要两个初始化权重矩阵。矩阵的维度units_next x units
      捕获.PNG

    隐藏层使用ReLU线性整流,损失采用交叉熵。对测试数据的准确率提升到约为98%。
    感知机代码

    相关文章

      网友评论

          本文标题:# tensorflow实战笔记(一)

          本文链接:https://www.haomeiwen.com/subject/rubnpxtx.html