octave-bug-tracker
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Octave-bug-tracker] [bug #60237] Differente behaviour in anonymous func


From: Denis Sbragion
Subject: [Octave-bug-tracker] [bug #60237] Differente behaviour in anonymous function handling
Date: Mon, 15 Mar 2021 12:33:18 -0400 (EDT)
User-agent: Mozilla/5.0 (Windows NT 6.1; Win64; x64; rv:85.0) Gecko/20100101 Firefox/85.0

URL:
  <https://savannah.gnu.org/bugs/?60237>

                 Summary: Differente behaviour in anonymous function handling 
                 Project: GNU Octave
            Submitted by: dsbragion
            Submitted on: Mon 15 Mar 2021 04:33:16 PM UTC
                Category: Interpreter
                Severity: 3 - Normal
                Priority: 5 - Normal
              Item Group: Regression
                  Status: None
             Assigned to: None
         Originator Name: 
        Originator Email: 
             Open/Closed: Open
                 Release: 6.2.0
         Discussion Lock: Any
        Operating System: Microsoft Windows

    _______________________________________________________

Details:

Hello,

I'm working with the NLopt optimization library (https://nlopt.readthedocs.io)
and I get a different behaviour going from 5.2.0 to 6.2.0. First of all, NLOpt
has been compiled outside of Octave using mingw64, so the NLopt binary library
used for both cases is the same.

Under 5.2.0 the following code works:


# NLOPT Based

# Initializes the optimization structure
op = struct();

# Set the algorithm to SQP
op.algorithm = NLOPT_LD_SLSQP;

# Set the objective function
op.min_objective = (@(t)(qestnlopt(t(:),nl,p,f,cl,gl,mm,0.5 * ol)));

# Set the tolerances for the optimization
op.ftol_rel = ol;
op.xtol_rel = ol;

# Set the lower and upper bound
op.lower_bounds = zeros(p,1);
op.upper_bounds = ones(p,1);

# Gradient of the equality constraint
eg = ones(p,1);

# Set the equality constraints function
op.h = { @(t)(qestnlopteq(t,sl' * ones(p,1),eg)) };

# Set the tolerances for the equality constraints
op.h_tol = ol;

# Set the sorting inequality constraints function
op.fc = cell(p - 1,1);
for (r = (1:(p - 1)))
        op.fc(r) = (@(t)(qestnloptne(t,r,p)));
endfor

# Set the tolerances for the sorting inequality constraints
op.fc_tol = repmat(ol,p - 1,1);

# Optimize
[ pl, se ] = nlopt_optimize(op,sl);


Under 6.2.0 I get the following error:


error: 'nl' undefined near line 173, column 173
error: called from
    nlscov>@<anonymous> at line 173 column 29
    nlscov at line 202 column 15


It looks like Octave no longer sees the variables passed from context to the
anonymous functions. At first I thought it was a NLopt bug but then I changed
the code above to the following one:


# NLOPT Based

# Initializes the optimization structure
op = struct();

# Set the algorithm to SQP
op.algorithm = NLOPT_LD_SLSQP;

function [ r, v ] = lobjf(t)
        if (isargout(2) == true)
                [ r, v ] = qestnlopt(t(:),nl,p,f,cl,gl,mm,0.5 * ol);
        else
                r = qestnlopt(t(:),nl,p,f,cl,gl,mm,0.5 * ol);
        endif
endfunction

# Set the objective function
# op.min_objective = (@(t)(qestnlopt(t(:),nl,p,f,cl,gl,mm,0.5 * ol))); <--
CHANGED
op.min_objective = @lobjf;

# Set the tolerances for the optimization
op.ftol_rel = ol;
op.xtol_rel = ol;

# Set the lower and upper bound
op.lower_bounds = zeros(p,1);
op.upper_bounds = ones(p,1);

# Gradient of the equality constraint
eg = ones(p,1);

# Set the equality constraints function
# op.h = { @(t)(qestnlopteq(t,sl' * ones(p,1),eg)) }; <-- CHANGED
op.h = { str2func([ '@(t)(qestnlopteq(t,' num2str(sl' * ones(p,1)) ',ones('
num2str(p) ',1)))' ]) };

# Set the tolerances for the equality constraints
op.h_tol = ol;

# Set the sorting inequality constraints function
op.fc = cell(p - 1,1);
for (r = (1:(p - 1)))
        # op.fc(r) = (@(t)(qestnloptne(t,r,p))); <-- CHANGED
        op.fc(r) = str2func([ '@(t)(qestnloptne(t,' num2str(r) ',' num2str(p) 
'))'
]);
endfor

# Set the tolerances for the sorting inequality constraints
op.fc_tol = repmat(ol,p - 1,1);

# Optimize
[ pl, se ] = nlopt_optimize(op,sl);


With these changes it works also under 6.2.0 (and no longer works under 5.2.0
beacause handles to nested functions aren't supported, but this is expected).
AFAIK if it was an NLopt bug it shouldn't work either in the second case. I
know also that some changes to anonymous functions handling hsa been
introduced since version 6, see for example bug #59989.

On the other hand, optimizing using the optim package, which also requires a
similar approach with anonymous functions and some function parameters passed
from context, works without problems both in 5.2.0 and 6.2.0, which is the
reason why I initially thought it was an NLopt bug.

I tried to reproduce the error with some simpler code, hopefully not involving
external libraries, to no avail. If someone might provide some hint I might
try harder.

Hope it helps.

Bye,

Denis Sbragion




    _______________________________________________________

Reply to this item at:

  <https://savannah.gnu.org/bugs/?60237>

_______________________________________________
  Message sent via Savannah
  https://savannah.gnu.org/




reply via email to

[Prev in Thread] Current Thread [Next in Thread]