 # SimulatedAnnealing (and SAMIN) claims "Status Failure", but output seems to be OK?

I am trying to get SimulatedAnnealing to work for an optimisation problem, so I first look at a basic example.

``````using Optim
f(x) = (1.0 - x)^2 + 100.0 * (x - x^2)^2
``````

This works fine:

``````x0 = [0.0,0.0]
``````

and the output claims success:

`````` * Status: success

* Candidate solution
Final objective value:     3.525527e-09

* Found with

* Convergence measures
√(Σ(yᵢ-ȳ)²)/n ≤ 1.0e-08

* Work counters
Seconds run:   0  (vs limit Inf)
Iterations:    60
f(x) calls:    117
``````

Next, I try using SimulatedAnnealing (with boundaries):

``````x0 = [0.0,0.0]
lb = [-100.0, -100.0]
ub = [100.0, 100.0]
res = optimize(f, lb, ub, x0, SAMIN(), Optim.Options(iterations=10^6))
``````

the output claims that this was a failure (`Status: failure`):

``````================================================================================
SAMIN results
==> Normal convergence <==
total number of objective function evaluations: 23101

Obj. value:      0.0000000000

parameter      search width
1.00000           0.00000
1.00000           0.00000
================================================================================

* Status: failure

* Candidate solution
Final objective value:     3.005018e-17

* Found with
Algorithm:     SAMIN

* Convergence measures
|x - x'|               = NaN ≰ 0.0e+00
|x - x'|/|x'|          = NaN ≰ 0.0e+00
|f(x) - f(x')|         = NaN ≰ 0.0e+00
|f(x) - f(x')|/|f(x')| = NaN ≰ 0.0e+00
|g(x)|                 = NaN ≰ 0.0e+00

* Work counters
Seconds run:   1  (vs limit Inf)
Iterations:    23101
f(x) calls:    23101
∇f(x) calls:   0
``````

however, the minimizer is still good, with `res.minimizer` = `[0.9999999587029669, 0.9999999176131619]`.

Finally, I try normal SimulatedAnnealing:

``````x0 = [0.0,0.0]
res = optimize(f, x0, SimulatedAnnealing(), Optim.Options(iterations=10^6))
``````

again the output claims failure, and this time gives a reason; `(reached maximum number of iterations)`. Again, the minimizer is actually good (`= [0.9999999587029669, 0.9999999176131619]`).

What is going on here? This seems like a simple problem (I tried to use this one: Optim.jl). Also, why is it claiming failure while the result seems to be good, am I missing something?

1 Like

You are correct, running the example from the documentation at Optim.jl/samin.md at master · JuliaNLSolvers/Optim.jl · GitHub

``````using Optim, OptimTestProblems

prob = UnconstrainedProblems.examples["Rosenbrock"];
res = Optim.optimize(prob.f, fill(-100.0, 2), fill(100.0, 2), prob.initial_x, SAMIN(), Optim.Options(iterations=10^6))
println(res)
``````

I also see

``````================================================================================
SAMIN results
==> Normal convergence <==
total number of objective function evaluations: 22451

Obj. value:      0.0000000000

parameter      search width
1.00000           0.00000
1.00000           0.00000
================================================================================

* Status: failure

* Candidate solution
Final objective value:     1.178874e-15

* Found with
Algorithm:     SAMIN

* Convergence measures
|x - x'|               = NaN ≰ 0.0e+00
|x - x'|/|x'|          = NaN ≰ 0.0e+00
|f(x) - f(x')|         = NaN ≰ 0.0e+00
|f(x) - f(x')|/|f(x')| = NaN ≰ 0.0e+00
|g(x)|                 = NaN ≰ 0.0e+00

* Work counters
Seconds run:   1  (vs limit Inf)
Iterations:    22451
f(x) calls:    22451
∇f(x) calls:   0
``````

Furthermore the documentation and current reporting differ and in the documentation I miss the status information signalling success or failure.

This seems to be a problem of SAMIN not fitting into Optim’s general scheme for checking convergence. SAMIN does not use gradients, so the gradient check failing may be normal, as SAMIN does not compute or return a gradient. However, its internal convergence criteria do require that the change in the parameter vector and the change in the function value lie within tolerances (either default or user provided). The source code has the lines

``````            # last value close enough to last neps values?
fstar = f_old
test = 0
for i=1:neps
test += (abs(f_old - fstar[i]) > f_tol)
end
test = (test > 0) # if different from zero, function conv. has failed
# last value close enough to overall best?
if (((fopt - f_old) <= f_tol) && (!test))
# check for bound narrow enough for parameter convergence
for i = 1:n
if (bounds[i] > x_tol)
converge = 0 # no conv. if bounds too wide
break
else
converge = 1
end
end
end
``````

which check for convergence. So, I think that the problem is that SAMIN’s output must not be providing enough information to allow Optim’s general method of checking convergence to work properly.

However, SAMIN has converged to a point inside the bounds if you see

`==> Normal convergence <==`

The only remaining concern is that the temperature reduction (rt) may be too low, which could cause SAMIN to skip over local minima which may be better than the one that is reported. If in doubt, set rt to a number closer to but less than 1.0. This will increase the time spent, but is safer for irregular objective functions.

1 Like

Thanks,

I am looking at simply using SAMIN now, and ignoring that part of the output message.