

私は詳解ディープラーニングという書籍を使いtensorflowの学習を行っています.

そこで疑問なのですが,データを正規化させて重みにも1/√nをかけて実行したのですが正解率が正規化する前よりも下がってしまいまいした.その理由がわからないので教えていただきたいです.

自分では,重みの初期値の設定の仕方が間違っている可能性があると思っていますが,具体的にどう間違っているのかがわかりません.

なおこの学習で用いたモデルは隠れ層3層  
ノード数全て200  
活性化関数relu  
出力層softmax  
誤差関数SGDを用いました.

この実装では正答率はだいたい70~80%でした.  
正規化を行わない場合全く同じモデルで94%以上でした.  
以下コードです.(正規化を行ったコードです.)

[code]

    import tensorflow as tf
    import numpy as np
    from sklearn.datasets import fetch_mldata
    from sklearn.model_selection import train_test_split
    from sklearn.utils import shuffle
    mnist = fetch_mldata('MNIST original', data_home = '.')
    
    class DNN(object):
      def __init__(self, n_in, n_hiddens, n_out):
        self.n_in = n_in
        self.n_out = n_out
        self.n_hiddens = n_hiddens
        self.weight = []
        self.bias = []
    
        self._x = None
        self._y = None
        self._t = None
        self._sess = None
        self._keep_prob = None
        self._history = {
            'loss':[],
            'accuracy':[]
        }
    
    
    
      def weight_variable(self,shape):
        #initial = tf.truncated_normal(shape, stddev=0.01)
        initial = np.sqrt(1.0 / shape[0]) * tf.truncated_normal(shape)
        return tf.Variable(initial)
    
      def bias_variable(self,shape):
        initial = tf.zeros(shape)
        return tf.Variable(initial)
    
      def inference(self, x, keep_prob):
        for i,n_hidden in enumerate(self.n_hiddens):
          if i == 0:
            input = x
            input_dim = self.n_in
    
          else:
    
            input = output
            input_dim = self.n_hiddens[i-1]
    
          self.weight.append(self.weight_variable([input_dim, n_hidden]))
          self.bias.append(self.bias_variable([n_hidden]))
    
          h = tf.nn.relu(tf.matmul(input, self.weight[-1]) + self.bias[-1])
          output = tf.nn.dropout(h, keep_prob)
    
        self.weight.append(
            self.bias_variable([self.n_hiddens[-1], self.n_out]))
        self.bias.append(self.bias_variable([self.n_out]))
    
        y = tf.nn.softmax(tf.matmul(
        output, self.weight[-1]) + self.bias[-1])
    
        return y
    
      def loss(self, y, t):
        cross_entropy = tf.reduce_mean(-tf.reduce_sum(t * tf.log(y),axis = 1))
        return cross_entropy
    
      def training(self,loss):
        optimizer = tf.train.GradientDescentOptimizer(0.01)
        train_step = optimizer.minimize(loss)
        return train_step
    
      def accuracy(self,y,t):
        correct_prediction = tf.equal(tf.argmax(y, 1), tf.argmax(t, 1))
        accuracy = tf.reduce_mean(tf.cast(correct_prediction, tf.float32))
        return accuracy
    
      def fit(self, X_train, Y_train,
              nb_epoch=100, batch_size=100, p_keep=0.5):
    
        x = tf.placeholder(tf.float32, shape = [None, self.n_in])
        t = tf.placeholder(tf.float32, shape = [None, self.n_out])
        keep_prob = tf.placeholder(tf.float32)
    
        self._x = x
        self._t = t
        self._keep_prob = keep_prob
    
    
        y = self.inference(x, keep_prob)
        loss = self.loss(y, t)
        train_step = self.training(loss)
        accuracy = self.accuracy(y, t)
    
        init = tf.global_variables_initializer()
        sess = tf.Session()
        sess.run(init)
    
        self._sess = sess
        self._y = y
    
        for epoch in range(nb_epoch):
          X_, Y_ = shuffle(X_train,Y_train)
    
          for i in range(len(X_train) // batch_size):
    
            start = i * batch_size
            end = start + batch_size
    
            sess.run(train_step, feed_dict = {
                x:X_[start:end],
                t:Y_[start:end],
                keep_prob:p_keep
            })
    
          loss_ = loss.eval(session = self._sess, feed_dict = {
              x:X_train,
              t:Y_train,
              keep_prob:1.0
          })
    
          accuracy_ = accuracy.eval(session = self._sess, feed_dict = {
              x:X_train,
              t:Y_train,
              keep_prob:1.0
          })
    
          self._history['loss'].append(loss_)
          self._history['accuracy'].append(accuracy_)
    
          print('epoch:', epoch,
                ' loss:', loss_,
                ' accuracy:', accuracy_)
    
        return self._history
    
      def evaluate(self, X_test, Y_test):
        accuracy = self.accuracy(self._y,self._t)
        return accuracy.eval(session = self._sess, feed_dict = {
              self._x:X_test,
              self._t:Y_test,
              self._keep_prob:1.0
          })
    
    
    if __name__ == '__main__':
    
      n = len(mnist.data)
      N = 10000  # MNISTの一部を使う
      indices = np.random.permutation(range(n))[:N]  # ランダムにN枚を選択
    
      X = mnist.data[indices]
      #X = X / X.max()
      #X = X - X.mean(axis = 1).reshape(len(X),1)
    
      X = X / 255.0
      X = X - X.mean(axis=1).reshape(len(X), 1)
    
      y = mnist.target[indices]
      Y = np.eye(10)[y.astype(int)]  # 1-of-K 表現に変換
    
      X_train, X_test, Y_train, Y_test = train_test_split(X, Y, train_size=0.8)
    
      '''
      モデル設定
      '''
    
      model = DNN(n_in=len(X[0]),
                  n_hiddens=[200, 200, 200],
                  n_out=len(Y[0]))
    
      '''
      モデル学習
      '''
      model.fit(X_train, Y_train,
                nb_epoch=50,
                batch_size=200,
                p_keep=0.5)
    
      '''
      予測精度の評価
      '''
      accuracy = model.evaluate(X_test, Y_test)
      print('accuracy: ', accuracy)
    
[/code]

ご教示のほどよろしくお願いいたします.


CC BY-SA 4.0
2019-01-01T17:34:45.547
51654
2019-01-01T17:34:45.547
31609
question
python 機械学習 tensorflow 深層学習
tensolflowでmnistの学習　データの正規化について