損失関数は減少するのではなく増加します

Dec0Ded:

私は最初から自分のニューラルネットワークを作るしようとしています。しばらくすると、私はそれを作ったが、私は解決できない問題に遭遇します。私は、次のされているチュートリアルこれを実行する方法を示しています。私はに実行する問題は、私のネットワークは、重みとバイアスを更新する方法でした。まあ、私は、勾配降下は常に損失を低減されることはありませんし、いくつかのエポックのために、それも少し増やす可能性があることを知って、それはまだはるかに良い鉱山はよりも減少し、作業すべきビット。時々 、全体のプロセスは損失9と13の上に立ち往生し、それから抜け出すことができません。私は多くのチュートリアル、ビデオ、ウェブサイトをチェックしましたが、私は私のコードでは何も間違って見つけることができませんでした。 self.activateself.dactivateself.lossself.dloss

# sigmoid
self.activate = lambda x: np.divide(1, 1 + np.exp(-x))
self.dactivate = lambda x: np.multiply(self.activate(x), (1 - self.activate(x)))

# relu
self.activate = lambda x: np.where(x > 0, x, 0)
self.dactivate = lambda x: np.where(x > 0, 1, 0)

# loss I use (cross-entropy)
clip = lambda x: np.clip(x, 1e-10, 1 - 1e-10) # it's used to squeeze x into a probability between 0 and 1 (which I think is required)
self.loss = lambda x, y: -(np.sum(np.multiply(y, np.log(clip(x))) + np.multiply(1 - y, np.log(1 - clip(x))))/y.shape[0])
self.dloss = lambda x, y: -(np.divide(y, clip(x)) - np.divide(1 - y, 1 - clip(x)))

私はforwardpropagationに使用するコード:

self.activate(np.dot(X, self.weights) + self.biases) # it's an example for first hidden layer

そして、それはバックプロパゲーションのためのコードです:

最初の部分、DenseNeuralNetworkクラス:

last_derivative = self.dloss(output, y)

for layer in reversed(self.layers):
    last_derivative = layer.backward(last_derivative, self.lr)

そして第二部、中Denseクラス:

def backward(self, last_derivative, lr):
    w = self.weights

    dfunction = self.dactivate(last_derivative)
    d_w = np.dot(self.layer_input.T, dfunction) * (1./self.layer_input.shape[1])
    d_b = (1./self.layer_input.shape[1]) * np.dot(np.ones((self.biases.shape[0], last_derivative.shape[0])), last_derivative)

    self.weights -= np.multiply(lr, d_w)
    self.biases -= np.multiply(lr, d_b)

    return np.dot(dfunction, w.T)

私も作ったREPLを使用すると、コード全体をチェックし、何の問題もなく、それを実行できるようにします。

ddoGas:

1。

ライン12

self.dloss = lambda x, y: -(np.divide(y, clip(x)) - np.divide(1 - y, 1 - clip(x)))

あなたがXをクリップするつもりなら、あなたはあまりにもYをクリップshoud。
私はこれを実装するにはいくつかの方法がありますが、あなたがこの方法を使用しようとしている場合を意味します。
への変更

self.dloss = lambda x, y: -(np.divide(clip(y), clip(x)) - np.divide(1 - clip(y), 1 - clip(x)))

2。

ライン75

dfunction = self.dactivate(last_derivative)

このバックプロパゲーション部分はちょうど間違っています。
への変更

dfunction = last_derivative*self.dactivate(np.dot(self.layer_input, self.weights) + self.biases)

3。

ライン77

d_b = (1./self.layer_input.shape[1]) * np.dot(np.ones((self.biases.shape[0], last_derivative.shape[0])), last_derivative)

last_derivativeはdfunctionでなければなりません。私は、これは単なる間違いだと思います。
への変更

d_b = (1./self.layer_input.shape[1]) * np.dot(np.ones((self.biases.shape[0], last_derivative.shape[0])), dfunction)

4。

ライン85

self.weights = np.random.randn(neurons, self.neurons) * np.divide(6, np.sqrt(self.neurons * neurons))
self.biases = np.random.randn(1, self.neurons) * np.divide(6, np.sqrt(self.neurons * neurons))

わからないどこにこれを行っているが、私は初期化された値が大きすぎると思います。私はちょうどそれが小さくなるように、我々は、正確なhypertuningをやっていません。

self.weights = np.random.randn(neurons, self.neurons) * np.divide(6, np.sqrt(self.neurons * neurons)) / 100
self.biases = np.random.randn(1, self.neurons) * np.divide(6, np.sqrt(self.neurons * neurons)) / 100

今すぐすべての良いです

この後、それが遅いことだったので、私は0.01に学習率を変更し、それが正常に働きました。
私はあなたが戻って伝播を誤解していると思います。あなたはおそらく、二重、それがどのように機能するかを確認する必要があります。他の部分は、私が考えてOKです。

おすすめ

転載: http://43.154.161.224:23101/article/api/json?id=26636&siteId=1