Java 反向传播算法
我在网上找到了一个示例,其中包含一个方法,可以反向传播错误并调整权重。我想知道这到底是如何工作的,以及使用了什么权重更新算法。可能是梯度下降吗Java 反向传播算法,java,algorithm,neural-network,backpropagation,gradient-descent,Java,Algorithm,Neural Network,Backpropagation,Gradient Descent,我在网上找到了一个示例,其中包含一个方法,可以反向传播错误并调整权重。我想知道这到底是如何工作的,以及使用了什么权重更新算法。可能是梯度下降吗 /** * all output propagate back * * @param expectedOutput * first calculate the partial derivative of the error with * respect to each of t
/**
* all output propagate back
*
* @param expectedOutput
* first calculate the partial derivative of the error with
* respect to each of the weight leading into the output neurons
* bias is also updated here
*/
public void applyBackpropagation(double expectedOutput[]) {
// error check, normalize value ]0;1[
for (int i = 0; i < expectedOutput.length; i++) {
double d = expectedOutput[i];
if (d < 0 || d > 1) {
if (d < 0)
expectedOutput[i] = 0 + epsilon;
else
expectedOutput[i] = 1 - epsilon;
}
}
int i = 0;
for (Neuron n : outputLayer) {
ArrayList<Connection> connections = n.getAllInConnections();
for (Connection con : connections) {
double ak = n.getOutput();
double ai = con.leftNeuron.getOutput();
double desiredOutput = expectedOutput[i];
double partialDerivative = -ak * (1 - ak) * ai
* (desiredOutput - ak);
double deltaWeight = -learningRate * partialDerivative;
double newWeight = con.getWeight() + deltaWeight;
con.setDeltaWeight(deltaWeight);
con.setWeight(newWeight + momentum * con.getPrevDeltaWeight());
}
i++;
}
// update weights for the hidden layer
for (Neuron n : hiddenLayer) {
ArrayList<Connection> connections = n.getAllInConnections();
for (Connection con : connections) {
double aj = n.getOutput();
double ai = con.leftNeuron.getOutput();
double sumKoutputs = 0;
int j = 0;
for (Neuron out_neu : outputLayer) {
double wjk = out_neu.getConnection(n.id).getWeight();
double desiredOutput = (double) expectedOutput[j];
double ak = out_neu.getOutput();
j++;
sumKoutputs = sumKoutputs
+ (-(desiredOutput - ak) * ak * (1 - ak) * wjk);
}
double partialDerivative = aj * (1 - aj) * ai * sumKoutputs;
double deltaWeight = -learningRate * partialDerivative;
double newWeight = con.getWeight() + deltaWeight;
con.setDeltaWeight(deltaWeight);
con.setWeight(newWeight + momentum * con.getPrevDeltaWeight());
}
}
}
/**
*所有输出都会传回
*
*@param预期输出
*首先计算误差的偏导数
*关于引入输出神经元的每个权重
*这里也更新了偏差
*/
public void applyBackpropagation(双预期输出[]){
//错误检查,标准化值]0;1[
for(int i=0;i1){
if(d<0)
期望输出[i]=0+ε;
其他的
期望输出[i]=1-ε;
}
}
int i=0;
用于(神经元n:输出层){
ArrayList connections=n.getAllInConnections();
用于(连接con:connections){
double ak=n.getOutput();
double ai=con.leftNeuron.getOutput();
双期望输出=期望输出[i];
双部分导数=-ak*(1-ak)*ai
*(期望输出-ak);
双三角权重=-学习率*部分导数;
double newWeight=con.getWeight()+deltaWeight;
con.设置三角重量(三角重量);
con.setWeight(newWeight+动量*con.getPrevDeltaWeight());
}
i++;
}
//更新隐藏层的权重
用于(神经元n:隐藏层){
ArrayList connections=n.getAllInConnections();
用于(连接con:connections){
double aj=n.getOutput();
double ai=con.leftNeuron.getOutput();
双功耗输出=0;
int j=0;
用于(神经元输出:输出层){
double wjk=out_neu.getConnection(n.id).getWeight();
双期望输出=(双)期望输出[j];
double ak=out_neu.getOutput();
j++;
sumKoutputs=sumKoutputs
+(((期望输出-ak)*ak*(1-ak)*wjk);
}
双偏导数=aj*(1-aj)*ai*求和输出;
双三角权重=-学习率*部分导数;
double newWeight=con.getWeight()+deltaWeight;
con.设置三角重量(三角重量);
con.setWeight(newWeight+动量*con.getPrevDeltaWeight());
}
}
}
这篇看起来很难看的文章似乎描述了完全相同的算法版本:。我在大学论文中有相同的公式,但遗憾的是:a)它们不能在线获得;b)它们使用的语言你不会理解
至于梯度下降,该算法类似于梯度下降,但不能保证达到最佳位置。在每一步中,都会对网络边进行更改,更改它们的值,从而增加训练示例值的概率。在我看来,该解决方案使用了。它与常规梯度的主要区别在于Delegate是对每个示例近似梯度,而不是对所有示例计算梯度,然后选择最佳方向。这是实现反向传播的常用方法,甚至对梯度下降有一些好处(可以避免某些局部极小值)。我相信这篇文章也解释了这个想法,还有很多其他文章解释了反向传播背后的主要思想。据我所知,这代表了一个带有一个隐藏层的MLP。如果无法遵循此代码,我猜反向传播将导致梯度下降。你的具体想法是什么问题?如果你能使用这个代码或者梯度下降是什么?如果这是SGD,那么训练样本上的循环在哪里?输出单元上有一个循环,它递增
i
,好像输出单元的数量等于训练样本的数量,这看起来完全荒谬。我认为应该有一个循环叫做g这个函数,实际上这个函数只对一个样本调整权重。这可以从函数的唯一输入是所有输出感知器的期望值(每个神经元只有一个值)这一事实中得出。啊,对了!我期望expectedOutput
具有长度n个样本
。