NLopt.jl icon indicating copy to clipboard operation
NLopt.jl copied to clipboard

Problems with LN_PRAXIS, GN_DIRECT and others...

Open lruthotto opened this issue 8 years ago • 3 comments

I've been experimenting with this package to compare some optimization methods (global/ local and with/without derivatives). I apologize if this is a dumb comment (since it's my first experience with NLopt), but I ran into some difficulties.

My first objective was to follow README.md and find a minimizer of the Himmelblau function. Here is what I tried:

using NLopt

count = 0 # keep track of # function evaluations

function Himmelblau(x::Vector,grad::Vector=[])
    if !isempty(grad)&& length(grad)>0
        grad[1] = 4*(x[1]^2+x[2]-11)*x[1]+2*(x[1]+x[2]^2-7)
        grad[2] = 2*(x[1]^2+x[2]-11)+4*(x[1]+x[2]^2-7)*x[2]
    end

    global count
    count::Int += 1
    
    (x[1]^2 +  x[2] - 11)^2 + (x[1] + x[2].^2 - 7).^2
end
opt = Opt(:GN_DIRECT, 2) # throws error
# opt = Opt(:LD_MMA, 2) # works fine

min_objective!(opt, Himmelblau)
x0 = [-0.1;-1]
(minf,minx,ret) = NLopt.optimize(opt,x0)

running this code, I get the following error (that I have a hard time understanding):

LoadError: ArgumentError: invalid NLopt arguments
while loading In[50], in expression starting on line 20

 in chk(::Int32) at ~/.julia/v0.5/NLopt/src/NLopt.jl:259
 in chks(::Int32) at ~/.julia/v0.5/NLopt/src/NLopt.jl:276
 in optimize!(::NLopt.Opt, ::Array{Float64,1}) at~/.julia/v0.5/NLopt/src/NLopt.jl:529
 in optimize(::NLopt.Opt, ::Array{Float64,1}) at ~/.julia/v0.5/NLopt/src/NLopt.jl:532

Is this a bug, or am I using NLopt incorrectly? If we get this to work, can I add this example (I have a longer ipynb with plots) to this repository?

lruthotto avatar Dec 16 '16 20:12 lruthotto

According to the NLopt documentation link: "Most of the above algorithms only handle bound constraints, and in fact require finite bound constraints (they are not applicable to unconstrained problems)."

So I would guess that you need to add constraints to your optimization. This README specifies how to do that, specifically: lower_bounds!(opt::Opt, lb::AbstractVector) upper_bounds!(opt::Opt, ub::AbstractVector)

stevenjgilmore avatar Jan 19 '17 04:01 stevenjgilmore

thanks for this, @stevenjgilmore ! Actually adding bound constraints makes a lot of sense here. I now add

lb = -4.*ones(2)
ub = 4.*ones(2)

lower_bounds!(opt,lb)
upper_bounds!(opt,ub)

to my example right before calling optimize. The previous error disappeared but now I get a Segmentation fault

signal (11): Segmentation fault: 11
while loading no file, in expression starting on line 0
unknown function (ip: 0xffffffffffffffff)
Allocations: 3345662 (Pool: 3344657; Big: 1005); GC: 4
Segmentation fault: 11

lruthotto avatar Jan 19 '17 12:01 lruthotto

This seems to already be an open issue: #64

Unfortunately it's unresolved. I'd recommend using a different algorithm for now

stevenjgilmore avatar Jan 19 '17 18:01 stevenjgilmore

Closing as stale, and because the error has since been improved. It is now:

julia> using NLopt

julia> count = 0 # keep track of # function evaluations
0

julia> function Himmelblau(x::Vector,grad::Vector=[])
           if !isempty(grad)&& length(grad)>0
               grad[1] = 4*(x[1]^2+x[2]-11)*x[1]+2*(x[1]+x[2]^2-7)
               grad[2] = 2*(x[1]^2+x[2]-11)+4*(x[1]+x[2]^2-7)*x[2]
           end

           global count
           count::Int += 1
           
           (x[1]^2 +  x[2] - 11)^2 + (x[1] + x[2].^2 - 7).^2
       end
Himmelblau (generic function with 2 methods)

julia> opt = Opt(:GN_DIRECT, 2) # throws error
Opt(GN_DIRECT, 2)

julia> # opt = Opt(:LD_MMA, 2) # works fine

       min_objective!(opt, Himmelblau)

julia> x0 = [-0.1;-1]
2-element Vector{Float64}:
 -0.1
 -1.0

julia> (minf,minx,ret) = NLopt.optimize(opt,x0)
ERROR: ArgumentError: invalid NLopt arguments: finite domain required for global algorithm
Stacktrace:
 [1] chk(o::Opt, result::Result)
   @ NLopt ~/.julia/dev/NLopt/src/NLopt.jl:212
 [2] optimize!(o::Opt, x::Vector{Float64})
   @ NLopt ~/.julia/dev/NLopt/src/NLopt.jl:624
 [3] optimize(o::Opt, x::Vector{Float64})
   @ NLopt ~/.julia/dev/NLopt/src/NLopt.jl:628
 [4] top-level scope
   @ REPL[10]:1

odow avatar Jan 25 '23 00:01 odow