data.setG0(y * y);
data.setGrad(grad.evaluate(startPosition));
data.setInverseHessianEsimate(getInitializedMatrix(startPosition));
if (!getNextPosition(function, grad, data)) {
throw new MathException("Cannot work with this starting position. Please choose another point");
}
int count = 0;
int resetCount = 1;
while (!isConverged(data)) {
if ((resetCount) % RESET_FREQ == 0) {
data.setInverseHessianEsimate(getInitializedMatrix(startPosition));
resetCount = 1;
} else {
_hessainUpdater.update(data);
}
if (!getNextPosition(function, grad, data)) {
data.setInverseHessianEsimate(getInitializedMatrix(startPosition));
resetCount = 1;
if (!getNextPosition(function, grad, data)) {
throw new MathException("Failed to converge in backtracking");
}
}
count++;
resetCount++;
if (count > _maxSteps) {
throw new MathException("Failed to converge after " + _maxSteps + " iterations. Final point reached: " + data.getX().toString());
}
}
return data.getX();
}