SCIP does not accept starting point of nonlinear objective from .nl file

I construct a nonlinear model in JuMP using the legacy and non-legacy interfaces, providing the same initial solution, and save the models to .nl files. SCIP is able to solve both .nl files correctly to optimality. SCIP accepts the initial solution provided in the legacy model .nl file, but does not accept the initial solution provided in the non-legacy model .nl file, as per the SCIP output below. The objective function value at the initial solution is approximately 988.4328858. It seems like SCIP is off by a constant offset when SCIP checks the feasibility of the initial solution provided for the non-legacy model: “violation: right hand side is violated by 988.43288588505
all 1 solutions given by solution candidate storage are infeasible”

SCIP accepts legacy model initial solution:

==> Solving problem 'model_legacy_N_16_zpad_2.nl' on 'leibniz121'
==> Solving started: 2024-06-10 17:59:44

SCIP version 8.0.3 [precision: 8 byte] [memory: block] [mode: optimized] [LP solver: Soplex 6.0.3] [GitHash: 62fab8a2e3]
Copyright (C) 2002-2022 Konrad-Zuse-Zentrum fuer Informationstechnik Berlin (ZIB)

External libraries: 
  Readline 8.0         GNU library for command line editing (gnu.org/s/readline)
  Soplex 6.0.3         Linear Programming Solver developed at Zuse Institute Berlin (soplex.zib.de) [GitHash: f900e3d0]
  CppAD 20180000.0     Algorithmic Differentiation of C++ algorithms developed by B. Bell (github.com/coin-or/CppAD)
  ZLIB 1.2.11          General purpose compression library by J. Gailly and M. Adler (zlib.net)
  GMP 6.2.0            GNU Multiple Precision Arithmetic Library developed by T. Granlund (gmplib.org)
  ZIMPL 3.5.3          Zuse Institute Mathematical Programming Language developed by T. Koch (zimpl.zib.de)
  AMPL/MP 4e2d45c4     AMPL .nl file reader library (github.com/ampl/mp)
  bliss 0.77           Computing Graph Automorphism Groups by T. Junttila and P. Kaski (www.tcs.hut.fi/Software/bliss/)

reading user parameter file <scip.set>
===========================

limits/time = 36000

read problem <model_legacy_N_16_zpad_2.nl>
============

original problem has 17 variables (0 bin, 16 int, 0 impl, 1 cont) and 1 constraints

solve problem
=============

1/1 feasible solution given by solution candidate storage, new primal bound 9.884329e+02

SCIP does not accept non-legacy model initial solution:

==> Solving problem 'model_non_legacy_N_16_zpad_2.nl' on 'leibniz121'
==> Solving started: 2024-06-10 18:00:28

SCIP version 8.0.3 [precision: 8 byte] [memory: block] [mode: optimized] [LP solver: Soplex 6.0.3] [GitHash: 62fab8a2e3]
Copyright (C) 2002-2022 Konrad-Zuse-Zentrum fuer Informationstechnik Berlin (ZIB)

External libraries: 
  Readline 8.0         GNU library for command line editing (gnu.org/s/readline)
  Soplex 6.0.3         Linear Programming Solver developed at Zuse Institute Berlin (soplex.zib.de) [GitHash: f900e3d0]
  CppAD 20180000.0     Algorithmic Differentiation of C++ algorithms developed by B. Bell (github.com/coin-or/CppAD)
  ZLIB 1.2.11          General purpose compression library by J. Gailly and M. Adler (zlib.net)
  GMP 6.2.0            GNU Multiple Precision Arithmetic Library developed by T. Granlund (gmplib.org)
  ZIMPL 3.5.3          Zuse Institute Mathematical Programming Language developed by T. Koch (zimpl.zib.de)
  AMPL/MP 4e2d45c4     AMPL .nl file reader library (github.com/ampl/mp)
  bliss 0.77           Computing Graph Automorphism Groups by T. Junttila and P. Kaski (www.tcs.hut.fi/Software/bliss/)

reading user parameter file <scip.set>
===========================

limits/time = 36000

read problem <model_non_legacy_N_16_zpad_2.nl>
============

original problem has 51 variables (16 bin, 0 int, 0 impl, 35 cont) and 35 constraints

solve problem
=============

  [nonlinear] <objcons>: ((1*(<x0>*<x0>)+1*(<x17>*<x17>)+(-8.2725)))^2+((1*(<x1>*<x1>)+1*(<x18>*<x18>)+(-8.2725)))^2+((1*(<x2>*<x2>)+1*(<x19>*<x19>)+(-8.2725)))^2+((1*(<x3>*<x3>)+1*(<x20>*<x20>)+(-8.2725)))^2+((1*(<x4>*<x4>)+1*(<x21>*<x21>)+(-6.34404)))^2+((1*(<x5>*<x5>)+1*(<x22>*<x22>)+(-6.34404)))^2+((1*(<x6>*<x6>)+1*(<x23>*<x23>)+(-6.34404)))^2+((1*(<x7>*<x7>)+1*(<x24>*<x24>)+(-6.34404)))^2+((1*(<x8>*<x8>)+1*(<x25>*<x25>)+(-6.34404)))^2+((1*(<x9>*<x9>)+1*(<x26>*<x26>)+(-6.34404)))^2+((1*(<x10>*<x10>)+1*(<x27>*<x27>)+(-6.34404)))^2+((1*(<x11>*<x11>)+1*(<x28>*<x28>)+(-6.34404)))^2+((1*(<x12>*<x12>)+1*(<x29>*<x29>)+(-6.34404)))^2+((1*(<x13>*<x13>)+1*(<x30>*<x30>)+(-6.34404)))^2+((1*(<x14>*<x14>)+1*(<x31>*<x31>)+(-6.34404)))^2+((1*(<x15>*<x15>)+1*(<x32>*<x32>)+(-6.34404)))^2+((1*(<x16>*<x16>)+1*(<x33>*<x33>)+(-6.34404)))^2-<nlobjvar> <= 0;
violation: right hand side is violated by 988.43288588505
all 1 solutions given by solution candidate storage are infeasible

Can you provide a reproducible example?

Below is Julia JuMP code that constructs and saves the legacy vs non-legacy nonlinear models (based on the Boolean use_legacy_model) with the same initial solution. In this example, the objective function value at the initial solution is 10204.25.

using JuMP

use_legacy_model = false # Whether to use legacy JuMP nonlinear constraints, expressions, and objectives.

N1 = 16
N = 16
zpad = 2
M = zpad*N

#s = rand(M,1)
#Br = rand(M, N1)
#Bi = rand(M, N1)

s = .5*ones(M,1)
Br = .8*ones(M, N1)
Bi = -.6*ones(M, N1)

Mt = trunc(Int,floor(M/2))+1
Br = Br[1:Mt,:]
Bi = Bi[1:Mt,:]
s = s[1:Mt]
Me = Mt

# Construct the JuMP model.
model_construction_time = @elapsed begin # Start elapsed.

model = Model()

@variable(model, y[1:N1], Bin)

if(~use_legacy_model)
        print("Constructing non-legacy model.\n")

        @expression(model, yh, y .- 0.5);
        @variable(model, spec_r[1:Mt])
        @variable(model, spec_i[1:Mt])
        @constraint(model, spec_r .== Br * yh)
        @constraint(model, spec_i .== Bi * yh)
        @expression(model, spec_sq_mag[m in 1:Mt], spec_r[m]^2 + spec_i[m]^2)
        @expression(model, gamma, sum((spec_sq_mag[m]-s[m])^2 for m in 1:Mt))
        @objective(model, Min, gamma)
else
        print("Constructing legacy model.\n")

        @expression(model, yh[n=1:N1], y[n]-.5)
        @expression(model, spec_r, Br*yh)
        @expression(model, spec_i, Bi*yh)

        @NLexpression(model, spec_sq_mag[m=1:Me], spec_r[m]^2 + spec_i[m]^2)

        @variable(model, gamma >= 0)

        @NLconstraint(model, gamma >= sum((spec_sq_mag[m]-s[m])^2 for m in 1:Me))
        @objective(model, Min, gamma)
end

end # End elapsed.
println("\nJuMP model construction time: $(model_construction_time) [s].")

# Construct an initial solution for the JuMP model.
y_vals = ones(N1,1)
y_vals[[5,10,15]] .= 0
set_start_value.(y, y_vals)

yh_vals = y_vals.-.5
spec_r_vals = Br*yh_vals
spec_i_vals = Bi*yh_vals
spec_sq_mag_vals = spec_r_vals.^2 .+ spec_i_vals.^2
gamma_val = sum((spec_sq_mag_vals.-s).^2)
if(~use_legacy_model)
        set_start_value.(spec_r, spec_r_vals)
        set_start_value.(spec_i, spec_i_vals)
else
        set_start_value(gamma, gamma_val)
        set_upper_bound(gamma, gamma_val)
end
println("\nJuMP model initialized with a feasible solution whose objective value is $(gamma_val).")


# Write the JuMP model to a .nl file.
model_write_time = @elapsed begin # Start elapsed.

write_to_file(model,"model.nl")

end # End elapsed.
println("\nJuMP model write time: $(model_write_time) [s].")

SCIP accepts legacy model initial solution:

==> Solving problem 'model_legacy_wis.nl' on 'leibniz121'
==> Solving started: 2024-06-10 20:17:34

SCIP version 8.0.3 [precision: 8 byte] [memory: block] [mode: optimized] [LP solver: Soplex 6.0.3] [GitHash: 62fab8a2e3]
Copyright (C) 2002-2022 Konrad-Zuse-Zentrum fuer Informationstechnik Berlin (ZIB)

External libraries: 
  Readline 8.0         GNU library for command line editing (gnu.org/s/readline)
  Soplex 6.0.3         Linear Programming Solver developed at Zuse Institute Berlin (soplex.zib.de) [GitHash: f900e3d0]
  CppAD 20180000.0     Algorithmic Differentiation of C++ algorithms developed by B. Bell (github.com/coin-or/CppAD)
  ZLIB 1.2.11          General purpose compression library by J. Gailly and M. Adler (zlib.net)
  GMP 6.2.0            GNU Multiple Precision Arithmetic Library developed by T. Granlund (gmplib.org)
  ZIMPL 3.5.3          Zuse Institute Mathematical Programming Language developed by T. Koch (zimpl.zib.de)
  AMPL/MP 4e2d45c4     AMPL .nl file reader library (github.com/ampl/mp)
  bliss 0.77           Computing Graph Automorphism Groups by T. Junttila and P. Kaski (www.tcs.hut.fi/Software/bliss/)

reading user parameter file <scip.set>
===========================

limits/time = 36000

read problem <model_legacy_wis.nl>
============

original problem has 17 variables (0 bin, 16 int, 0 impl, 1 cont) and 1 constraints

solve problem
=============

1/1 feasible solution given by solution candidate storage, new primal bound 1.020425e+04

SCIP does not accept non-legacy model initial solution:

==> Solving problem 'model_non_legacy_wis.nl' on 'leibniz121'
==> Solving started: 2024-06-10 20:18:00

SCIP version 8.0.3 [precision: 8 byte] [memory: block] [mode: optimized] [LP solver: Soplex 6.0.3] [GitHash: 62fab8a2e3]
Copyright (C) 2002-2022 Konrad-Zuse-Zentrum fuer Informationstechnik Berlin (ZIB)

External libraries: 
  Readline 8.0         GNU library for command line editing (gnu.org/s/readline)
  Soplex 6.0.3         Linear Programming Solver developed at Zuse Institute Berlin (soplex.zib.de) [GitHash: f900e3d0]
  CppAD 20180000.0     Algorithmic Differentiation of C++ algorithms developed by B. Bell (github.com/coin-or/CppAD)
  ZLIB 1.2.11          General purpose compression library by J. Gailly and M. Adler (zlib.net)
  GMP 6.2.0            GNU Multiple Precision Arithmetic Library developed by T. Granlund (gmplib.org)
  ZIMPL 3.5.3          Zuse Institute Mathematical Programming Language developed by T. Koch (zimpl.zib.de)
  AMPL/MP 4e2d45c4     AMPL .nl file reader library (github.com/ampl/mp)
  bliss 0.77           Computing Graph Automorphism Groups by T. Junttila and P. Kaski (www.tcs.hut.fi/Software/bliss/)

reading user parameter file <scip.set>
===========================

limits/time = 36000

read problem <model_non_legacy_wis.nl>
============

original problem has 51 variables (16 bin, 0 int, 0 impl, 35 cont) and 35 constraints

solve problem
=============

  [nonlinear] <objcons>: ((1*(<x0>*<x0>)+1*(<x17>*<x17>)+(-0.5)))^2+((1*(<x1>*<x1>)+1*(<x18>*<x18>)+(-0.5)))^2+((1*(<x2>*<x2>)+1*(<x19>*<x19>)+(-0.5)))^2+((1*(<x3>*<x3>)+1*(<x20>*<x20>)+(-0.5)))^2+((1*(<x4>*<x4>)+1*(<x21>*<x21>)+(-0.5)))^2+((1*(<x5>*<x5>)+1*(<x22>*<x22>)+(-0.5)))^2+((1*(<x6>*<x6>)+1*(<x23>*<x23>)+(-0.5)))^2+((1*(<x7>*<x7>)+1*(<x24>*<x24>)+(-0.5)))^2+((1*(<x8>*<x8>)+1*(<x25>*<x25>)+(-0.5)))^2+((1*(<x9>*<x9>)+1*(<x26>*<x26>)+(-0.5)))^2+((1*(<x10>*<x10>)+1*(<x27>*<x27>)+(-0.5)))^2+((1*(<x11>*<x11>)+1*(<x28>*<x28>)+(-0.5)))^2+((1*(<x12>*<x12>)+1*(<x29>*<x29>)+(-0.5)))^2+((1*(<x13>*<x13>)+1*(<x30>*<x30>)+(-0.5)))^2+((1*(<x14>*<x14>)+1*(<x31>*<x31>)+(-0.5)))^2+((1*(<x15>*<x15>)+1*(<x32>*<x32>)+(-0.5)))^2+((1*(<x16>*<x16>)+1*(<x33>*<x33>)+(-0.5)))^2-<nlobjvar> <= 0;
violation: right hand side is violated by 10204.25
all 1 solutions given by solution candidate storage are infeasible

How are you running SCIP?

Have you tried identical formulations? Currently, the two model.nl files will not be the same. One is an epigraph formulation, and one isn’t.

From what I can tell, the .nl file that gets written is correct, and it includes the starting points, so the issue might be in however you are loading and ruining SCIP.

I’m submitting the .nl file to COAP. https://www.coap.online/

Did you try changing the new version to also use the epigraph formulation (or the @NL version to use the non-epigraph?

I don’t know if we can help debug issues with COAP. You should contact their support.

I reported this issue at SCIP’s GitHub repo: SCIP v8.0.3 not accepting initial feasible solution · Issue #92 · scipopt/scip · GitHub

From Issues · scipopt/scip · GitHub

The issue has nothing to do with the legacy/non-legacy stuff, but the fact that you are using the non-epigraph formulation in the “non-legacy” model and the epigraph formulation in the “legacy” model.

If you want to use the new nonlinear interface, and you want to use SCIP, and you want the initial starting point: us the epigraph formulation in the new interface.

SCIP still does not accept the initial solution for the epigraph formulation with the new nonlinear interface, as per the output below. The epigraph model with the new nonlinear interface is constructed by modifying the previous code:

#@expression(model, gamma, sum((spec_sq_mag[m]-s[m])^2 for m in 1:Mt))
@variable(model, gamma >= 0)
@constraint(model, gamma >= sum((spec_sq_mag[m]-s[m])^2 for m in 1:Me))
==> Solving problem 'model_epi_non_legacy_wis.nl' on 'leibniz121'
==> Solving started: 2024-06-13 22:36:30

SCIP version 8.0.3 [precision: 8 byte] [memory: block] [mode: optimized] [LP solver: Soplex 6.0.3] [GitHash: 62fab8a2e3]
Copyright (C) 2002-2022 Konrad-Zuse-Zentrum fuer Informationstechnik Berlin (ZIB)

External libraries: 
  Readline 8.0         GNU library for command line editing (gnu.org/s/readline)
  Soplex 6.0.3         Linear Programming Solver developed at Zuse Institute Berlin (soplex.zib.de) [GitHash: f900e3d0]
  CppAD 20180000.0     Algorithmic Differentiation of C++ algorithms developed by B. Bell (github.com/coin-or/CppAD)
  ZLIB 1.2.11          General purpose compression library by J. Gailly and M. Adler (zlib.net)
  GMP 6.2.0            GNU Multiple Precision Arithmetic Library developed by T. Granlund (gmplib.org)
  ZIMPL 3.5.3          Zuse Institute Mathematical Programming Language developed by T. Koch (zimpl.zib.de)
  AMPL/MP 4e2d45c4     AMPL .nl file reader library (github.com/ampl/mp)
  bliss 0.77           Computing Graph Automorphism Groups by T. Junttila and P. Kaski (www.tcs.hut.fi/Software/bliss/)

reading user parameter file <scip.set>
===========================

limits/time = 36000

read problem <model_epi_non_legacy_wis.nl>
============

original problem has 51 variables (16 bin, 0 int, 0 impl, 35 cont) and 35 constraints

solve problem
=============

  [nonlinear] <nlc0>: <x0>-(((1*(<x1>*<x1>)+1*(<x18>*<x18>)+(-0.5)))^2+((1*(<x2>*<x2>)+1*(<x19>*<x19>)+(-0.5)))^2+((1*(<x3>*<x3>)+1*(<x20>*<x20>)+(-0.5)))^2+((1*(<x4>*<x4>)+1*(<x21>*<x21>)+(-0.5)))^2+((1*(<x5>*<x5>)+1*(<x22>*<x22>)+(-0.5)))^2+((1*(<x6>*<x6>)+1*(<x23>*<x23>)+(-0.5)))^2+((1*(<x7>*<x7>)+1*(<x24>*<x24>)+(-0.5)))^2+((1*(<x8>*<x8>)+1*(<x25>*<x25>)+(-0.5)))^2+((1*(<x9>*<x9>)+1*(<x26>*<x26>)+(-0.5)))^2+((1*(<x10>*<x10>)+1*(<x27>*<x27>)+(-0.5)))^2+((1*(<x11>*<x11>)+1*(<x28>*<x28>)+(-0.5)))^2+((1*(<x12>*<x12>)+1*(<x29>*<x29>)+(-0.5)))^2+((1*(<x13>*<x13>)+1*(<x30>*<x30>)+(-0.5)))^2+((1*(<x14>*<x14>)+1*(<x31>*<x31>)+(-0.5)))^2+((1*(<x15>*<x15>)+1*(<x32>*<x32>)+(-0.5)))^2+((1*(<x16>*<x16>)+1*(<x33>*<x33>)+(-0.5)))^2+((1*(<x17>*<x17>)+1*(<x34>*<x34>)+(-0.5)))^2) >= 0;
violation: left hand side is violated by 10204.25
all 1 solutions given by solution candidate storage are infeasible

Did you set a starting value for gamma?

No, I forgot to do that. I will try that now.

1 Like

SCIP now accepts the initial solution using the epigraph formulation with the new nonlinear interface, after setting the correct starting value for gamma. Thanks.

# Construct an initial solution for the JuMP model.
y_vals = ones(N1,1)
y_vals[[5,10,15]] .= 0
set_start_value.(y, y_vals)

yh_vals = y_vals.-.5
spec_r_vals = Br*yh_vals
spec_i_vals = Bi*yh_vals
spec_sq_mag_vals = spec_r_vals.^2 .+ spec_i_vals.^2
gamma_val = sum((spec_sq_mag_vals.-s).^2)
if(~use_legacy_model)
        set_start_value.(spec_r, spec_r_vals)
        set_start_value.(spec_i, spec_i_vals)
        set_start_value(gamma, gamma_val)
        set_upper_bound(gamma, gamma_val)
else
        set_start_value(gamma, gamma_val)
        set_upper_bound(gamma, gamma_val)
end
println("\nJuMP model initialized with a feasible solution whose objective value is $(gamma_val).")
==> Solving problem 'model_epi_non_legacy_wis.nl' on 'leibniz121'
==> Solving started: 2024-06-13 22:46:18

SCIP version 8.0.3 [precision: 8 byte] [memory: block] [mode: optimized] [LP solver: Soplex 6.0.3] [GitHash: 62fab8a2e3]
Copyright (C) 2002-2022 Konrad-Zuse-Zentrum fuer Informationstechnik Berlin (ZIB)

External libraries: 
  Readline 8.0         GNU library for command line editing (gnu.org/s/readline)
  Soplex 6.0.3         Linear Programming Solver developed at Zuse Institute Berlin (soplex.zib.de) [GitHash: f900e3d0]
  CppAD 20180000.0     Algorithmic Differentiation of C++ algorithms developed by B. Bell (github.com/coin-or/CppAD)
  ZLIB 1.2.11          General purpose compression library by J. Gailly and M. Adler (zlib.net)
  GMP 6.2.0            GNU Multiple Precision Arithmetic Library developed by T. Granlund (gmplib.org)
  ZIMPL 3.5.3          Zuse Institute Mathematical Programming Language developed by T. Koch (zimpl.zib.de)
  AMPL/MP 4e2d45c4     AMPL .nl file reader library (github.com/ampl/mp)
  bliss 0.77           Computing Graph Automorphism Groups by T. Junttila and P. Kaski (www.tcs.hut.fi/Software/bliss/)

reading user parameter file <scip.set>
===========================

limits/time = 36000

read problem <model_epi_non_legacy_wis.nl>
============

original problem has 51 variables (16 bin, 0 int, 0 impl, 35 cont) and 35 constraints

solve problem
=============

1/1 feasible solution given by solution candidate storage, new primal bound 1.020425e+04
1 Like

Glad you got it working.

I’ve edited the title of this post to reflect that it is unrelated to the legacy/non-legacy code in JuMP.