2017-10-09 16 views
1

私はしばらくの間ニューラルネットワークを研究しており、pythonとnumpyで実装しました。私はXORで非常に簡単な例を作ったし、うまくいきました。だから私はさらに進んで、MNISTデータベースを試してみることにしました。ニューラルネットワークMNIST

問題があります。私は、784個の入力、30個の隠れたニューロン、10個の出力ニューロンを持つNNを使用しています。 隠れ層の活性化機能は1つだけを吐き出すので、ネットワークは基本的に学習をやめます。私がやっている数学は正しいですし、同じ実装はXORの例でうまくいき、私は適切にMNISTを読んでいます。だから問題はどこから来ているのかわかりません。

import pickle 
import gzip 

import numpy as np 

def load_data(): 
    f = gzip.open('mnist.pkl.gz', 'rb') 
    training_data, validation_data, test_data = pickle.load(f, encoding="latin1") 
    f.close() 
    return (training_data, validation_data, test_data) 

def transform_output(num): 
    arr = np.zeros(10) 
    arr[num] = 1.0 
    return arr 

def out2(arr): 
    return arr.argmax() 


data = load_data() 
training_data = data[0] 
training_input = np.array(training_data[0]) 
training_output = [transform_output(y) for y in training_data[1]] 

batch_size = 10 

batch_count = int(np.ceil(len(training_input)/batch_size)) 

input_batches = np.array_split(training_input, batch_count) 
output_batches = np.array_split(training_output, batch_count) 

#Sigmoid Function 
def sigmoid (x): 
    return 1.0/(1.0 + np.exp(-x)) 

#Derivative of Sigmoid Function 
def derivatives_sigmoid(x): 
    return x * (1.0 - x) 

#Variable initialization 
epoch=1 #Setting training iterations 
lr=2.0 #Setting learning rate 
inputlayer_neurons = len(training_input[0]) #number of features in data set 
hiddenlayer_neurons = 30 #number of hidden layers neurons 

output_neurons = len(training_output[0]) #number of neurons at output layer 

#weight and bias initialization 
wh=np.random.uniform(size=(inputlayer_neurons,hiddenlayer_neurons)) 
bh=np.random.uniform(size=(1,hiddenlayer_neurons)) 
wout=np.random.uniform(size=(hiddenlayer_neurons,output_neurons)) 
bout=np.random.uniform(size=(1,output_neurons)) 

for i in range(epoch): 
    for batch in range(batch_count): 

     X = input_batches[batch] 
     y = output_batches[batch] 

     zh1 = np.dot(X, wh) 
     zh = zh1 + bh 

     # data -> hidden neurons -> activations 
     ah = sigmoid(zh) 

     zo1 = np.dot(ah, wout) 
     zo = zo1 + bout 

     output = sigmoid(zo) 

     # data -> output neurons -> error 
     E = y - output 

     print("debugging") 
     print("X") 
     print(X) 
     print("WH") 
     print(wh) 
     print("zh1") 
     print(zh1) 
     print("bh") 
     print(bh) 
     print("zh") 
     print(zh) 
     print("ah") 
     print(ah) 
     print("wout") 
     print(wout) 
     print("zo1") 
     print(zo1) 
     print("bout") 
     print(bout) 
     print("zo") 
     print(zo) 
     print("out") 
     print(output) 
     print("y") 
     print(y) 
     print("error") 
     print(E) 
     # data -> output neurons -> slope 
     slope_out = derivatives_sigmoid(output) 

     # data -> output neurons -> change of error 
     d_out = E * slope_out 

     # data -> hidden neurons -> error = data -> output neurons -> change of error DOT output neurons -> output inputs (equal to hidden neurons) -> weights 
     error_hidden = d_out.dot(wout.T) 

     # data -> hidden neurons -> slope 
     slope_h = derivatives_sigmoid(ah) 

     # data -> hidden neurons -> change of error 
     d_hidden = error_hidden * slope_h 

     # hidden neurons -> output neurons -> weights = "" + hidden neurons -> data -> activations DOT data -> output neurons -> change of error 
     wout = wout + ah.T.dot(d_out) * lr 
     bout = bout + np.sum(d_out, axis=0, keepdims=True) * lr 

     wh = wh + X.T.dot(d_hidden) * lr 
     bh = bh + np.sum(d_hidden, axis=0, keepdims=True) * lr 
    # testing results 
    X = np.array(data[1][0][0:10]) 
    zh1 = np.dot(X, wh) 
    zh = zh1 + bh 

    # data -> hidden neurons -> activations 
    ah = sigmoid(zh) 

    zo1 = np.dot(ah, wout) 
    zo = zo1 + bout 

    output = sigmoid(zo) 
    print([out2(y) for y in output]) 
    print(data[1][1][0:10]) 

ので、全体的なニューラルネットワークの出力は、入力毎に同じと速度と100のエポックを助けていない学習、異なるバッチサイズでそれを訓練しています。

答えて

1

XORとMNISTの問題の違いは、クラスの数です.XORはバイナリ分類で、MNISTには10のクラスがあります。

Eは、Sigmoid関数をバイナリのケースで使用できるため、XORで動作します。 2つ以上のクラスがある場合は、softmax function(シグモイドの拡張バージョン)とcross entropy lossを使用する必要があります。違いを見るにはthis questionを見てください。 yをワンホットエンコーディングに正しく変換しましたが、outputに予測確率分布が含まれていません。実際には、それぞれが非常に近い値のベクトルが含まれています(1.0に非常に近い)。それがネットワークが学ばない理由です。

+0

すばやくお返事ありがとうございます。私は次のチュートリアルのチュートリアルhttp://neuralnetworksanddeeplearning.com/chap1.htmlを使用しています。彼は私と同様のネットワークを使用しています。私はプレーン10の出力ニューロンとシグモイドを使用していて、最初のエポック後に約95%の成功率を得ています。私は彼のコードを辿り、私のものを比較して比較します。悪魔は詳細です。しかし、ええ、私はこの仕事ができるだけ早く、私は間違いなくsoftmax、ドロップアウト、およびrelusなどに行くでしょう – Johannes

+0

私は実際には、ネットワークが95%の精度を作ることができることに懐疑的です。彼の次の例では、ロジスティック回帰(私が示唆したもの)と畳み込みニューラルネットワーク(このような結果を示す可能性がより高い)を使用しています。しかし、あなたが間違っていることを証明して90%の精度に達することができれば、私に教えてください。私はこのネットワークを自分で試してみたいと思っています。 – Maxim

+0

私は彼のコードを実行し、私は最初のエポックの後に90%を繰り返し得ました。私がこれまで見てきた違いは、バッチサイズに応じて学習率を分け、バッチをランダム化するということです。しかし、これは私の問題を説明していません。私は何も得ていない、すべてのニューロンの活性化は隠された出力層ですべて1である – Johannes

関連する問題