我正在尝试使用here找到的教程在JavaScript中创建一个简单的前馈神经网络。我相信我正确地遵循了该教程,因为当我使用[[0,0,1],[0,1,1],[1,0,1],[1,1,1]]
的输入矩阵和[[0],[1],[1],[0]]
的解决方案矩阵对它进行培训时,网络可以按预期运行。但是,当我尝试使用MNIST handwritten number database训练网络并传递更大的矩阵时,输出数组中的所有元素都接近零。我怀疑这与输入数组的点积和权重返回填充有大量数字的数组有关,但是我尝试缩小这些数字的结果导致输出接近1。有人能找出答案吗?出问题了吗?我的神经网络只有一个包含300个神经元的隐藏层。下面的代码片段显示了我的神经网络的方法,因为我认为那是我要去的地方,但是如果您想查看我整个凌乱且未记录的程序,可以找到here。我不熟悉所使用的数学库,这意味着我制定了一些自己的方法来与数学方法配合使用。
我发现将权重设置为0到1之间的值会使损失保持在0.9,所以我现在使用“ randomlow”将其设置。
function NeuralNetwork(x, y){
//Initializing the neural network
this.input = x;
this.y = y;
this.sizes = [this.input._size[1], 300, this.y._size[1]];
this.layers = this.sizes.length - 1;
this.lyrs = [this.input];
this.weights = [];
this.dweights = [];
for(var i = 0; i < this.layers; i ++){
this.weights.push(new math.matrix());
this.weights[i].resize([this.sizes[i], this.sizes[i + 1]]);
this.weights[i] = setAll(this.weights[i], "randomlow");
}
this.output = new math.matrix();
this.output.resize(this.y._size);
};
NeuralNetwork.prototype.set = function(x, y){
//I train the network by looping through values from the database and passing them into this function
this.input = x;
this.lyrs = [this.input];
this.y = y;
};
NeuralNetwork.prototype.feedforward = function(){
//Looping through the layers and multiplying them by their respective weights
for(var i = 0; i < this.weights.length; i ++){
this.lyrs[i + 1] = math.multiply(this.lyrs[i], this.weights[i]);
this.lyrs[i + 1] = setAll(this.lyrs[i + 1], "sigmoid");
}
this.output = this.lyrs[this.lyrs.length - 1];
};
NeuralNetwork.prototype.backpropogate = function(){
//Backpropogating the network. I don't fully understand this part
this.antis = [
function(a, b, c){
return(
math.multiply(transposeMatrix(a[0]), multMatrices(math.multiply(multMatrices(math.multiply(math.subtract(b.y, b.output), 2), setAll(b.output, "sigmoidDerivitive")), transposeMatrix(c)), setAll(a[1], "sigmoidDerivitive")))
);
},
function(a, b, c){
return(
math.multiply(transposeMatrix(a[0]), multMatrices(math.multiply(math.subtract(b.y, b.output), 2), setAll(b.output, "sigmoidDerivitive")))
);
}];
this.input = [];
this.weightInput = 0;
for(var i = this.weights.length - 1; i >= 0; --i){
this.input.unshift(this.lyrs[i]);
this.weightInput = (i === this.weights.length - 1 ? 0 : this.weights[i + 1]);
this.dweights[i] = this.antis[i](this.input, this, this.weightInput);
}
for(var i = 0; i < this.dweights.length; i ++){
this.weights[i] = math.add(this.weights[i], this.dweights[i]);
}
};
一如既往,感谢您为解决我的问题所花费的时间。如果我的代码难以理解,请不要理会。 JavaScript可能不是达到此目的的最佳语言,但我不想遵循使用相同语言的教程。
编辑:这是this post的潜在重复,已得到解答。如果有人遇到这个问题,他们应该看看那里的答案是否有帮助。截至目前,我尚未在程序中对其进行测试。