Optim `Fminbox()` -- what is wrong

I’m trying to use Optim and Fminbox() for model fitting, but get an error message – and wonder what I do wrong. Here is what I do:

I have created a loss function loss(p) (squared norm of shooting error for ODE). As my initial guess, I have pvec given as:

julia> pvec
1-element Array{Real,1}:
 0.45

The loss function at the initial guess is:

julia> loss(pvec)
2.9500373651496017

I can plot the function:

P = range(pvec[1]*0.1,pvec[1]*50,length=100)
plot(P,loss.(P))

leading to:


I have defined lower and upper bounds:

p_lo = pvec*0.1;
p_up = pvec*100;

using Optim, I try to optimize the loss function:

julia> optimize(loss,p_lo,p_up,pvec,Fminbox())
MethodError: no method matching optimize(::getfield(Main, Symbol("##76#77")), ::Array{Float64,1}, ::Array{Float64,1}, ::Array{Real,1}, ::Fminbox{LBFGS{Nothing,LineSearches.InitialStatic{Float64},LineSearches.HagerZhang{Float64,Base.RefValue{Bool}},getfield(Optim, Symbol("##22#24"))},Float64,getfield(Optim, Symbol("##46#48"))})
Closest candidates are:
  optimize(::Any, ::AbstractArray{T<:AbstractFloat,N} where N, ::AbstractArray{T<:AbstractFloat,N} where N, !Matched::AbstractArray{T<:AbstractFloat,N} where N, ::Fminbox) where T<:AbstractFloat at C:\Users\user_name\.julia\packages\Optim\Agd3B\src\multivariate\solvers\constrained\fminbox.jl:163
  optimize(::Any, ::AbstractArray{T<:AbstractFloat,N} where N, ::AbstractArray{T<:AbstractFloat,N} where N, !Matched::AbstractArray{T<:AbstractFloat,N} where N, ::Fminbox, !Matched::Any; inplace, autodiff) where T<:AbstractFloat at C:\Users\user_name\.julia\packages\Optim\Agd3B\src\multivariate\solvers\constrained\fminbox.jl:163
  optimize(::Any, ::AbstractArray, ::AbstractArray, ::AbstractArray, !Matched::SAMIN) at C:\Users\user_name\.julia\packages\Optim\Agd3B\src\multivariate\solvers\constrained\samin.jl:60
  ...

Stacktrace:
 [1] top-level scope at In[189]:1

Question: what is it that I miss?

AHA!.. I suspect the problem is that pvec for some reason is of type Real instead of being of type Float64.

I constructed pvec by stripping out a subset of elements of a named tuple containing a mixture of floats and integers… essentially as follows:

julia> p = (a=1,b=2.,c=3)
(a = 1, b = 2.0, c = 3)

julia> idx = [1]
1-element Array{Int64,1}:
 1

julia> pvec = collect(p)[idx]
1-element Array{Real,1}:
 1

julia> idx = [2]
1-element Array{Int64,1}:
 2

julia> pvec = collect(p)[idx]
1-element Array{Real,1}:
 2.0

Is this intended behavior? I guess the solution around it is to make sure all values of the named tuple are real.

I’m a little puzzled by the result:

The suggested minimizer is approximately p = 15. From the plot, I would have expected a minimizer to be approximately p = 12.

Is the “problem” due to:

  • too low tolerances?
  • a somewhat unsmooth loss function?
  • other things?

I also tested the call optimize(loss,pvec,LBFGS()), i.e., without constraints. In that case, the suggested minimizer is p = 21.8.