# SOS1 Constraints in Bonmin Solver - JuMP / AmplNLWriter

**URL:** <https://discourse.julialang.org/t/sos1-constraints-in-bonmin-solver-jump-amplnlwriter/5450>\
**Category:** Optimization (Mathematical)\
**Tags:** question, jump\
**Created:** [August 18, 2017, 4:20pm UTC](https://discourse.julialang.org/t/sos1-constraints-in-bonmin-solver-jump-amplnlwriter/5450 "2017-08-18T16:20:15Z")\
**Posts on this page:** 8\
**Page:** 1

<div class="post-metadata">

**Author:** ![michaellindon](https://avatars.discourse-cdn.com/v4/letter/m/da6949/32.png) [@michaellindon](https://discourse.julialang.org/u/michaellindon)\
**Post date:** [August 18, 2017, 4:20pm UTC](https://discourse.julialang.org/t/sos1-constraints-in-bonmin-solver-jump-amplnlwriter/5450/1 "2017-08-18T16:20:15Z")

</div>

I would like to use Bonmin to perform MINLP. The model I have in mind has some SOS constraints of type 1. According to the [bonmin documentation](https://projects.coin-or.org/Bonmin/browser/stable/0.1/Bonmin/doc/BONMIN_UsersManual.pdf?format=raw) page 2, the B-BB algorithm accepts SOS1 constraints.

When I try to solve the model in JuMP I get the following error:

```julia
julia> solve(m)
ERROR: Not implemented for SOS constraints
Stacktrace:
 [1] constraintbounds(::JuMP.Model, ::JuMP.ProblemTraits) at /home/michael/.julia/v0.6/JuMP/src/solvers.jl:1033
 [2] _buildInternalModel_nlp(::JuMP.Model, ::JuMP.ProblemTraits) at /home/michael/.julia/v0.6/JuMP/src/nlp.jl:1243
 [3] #build#119(::Bool, ::Bool, ::JuMP.ProblemTraits, ::Function, ::JuMP.Model) at /home/michael/.julia/v0.6/JuMP/src/solvers.jl:303
 [4] (::JuMP.#kw##build)(::Array{Any,1}, ::JuMP.#build, ::JuMP.Model) at ./<missing>:0
 [5] #solve#116(::Bool, ::Bool, ::Bool, ::Array{Any,1}, ::Function, ::JuMP.Model) at /home/michael/.julia/v0.6/JuMP/src/solvers.jl:168
 [6] solve(::JuMP.Model) at /home/michael/.julia/v0.6/JuMP/src/solvers.jl:150
 [7] macro expansion at ./REPL.jl:97 [inlined]
 [8] (::Base.REPL.##1#2{Base.REPL.REPLBackend})() at ./event.jl:73

```

I have created a minimal reproducible example that solves the best subset selection problem. I solve this first using Gurobi, which works, and then with Bonmin, which fails.

```julia
using JuMP
using Distributions
using Gurobi
n=200
p=20
B=zeros(p)
B[1]=1
B[2]=2
B[3]=3
X=reshape(rand(Normal(0,1),n*p),n,p)
Y=X*B+rand(Normal(0,1),n)

#GUROBI

m = Model(solver=GurobiSolver())
@variable(m, B[1:p])
@variable(m, G[1:p], Bin)
@variable(m, Z[1:p], Bin)
for i=1:p
    addSOS1(m, [B[i],Z[i]])
end
@constraint(m, Z .== 1 .-G )
@constraint(m, sum(G[j] for j=1:p) <= 3)
@objective(m, Min, sum((Y[i]-sum( X[i,j]*B[j] for j=1:p))^2 for i=1:n))
solve(m)

#BONMIN

using AmplNLWriter
m = Model(solver=AmplNLSolver("bonmin", ["bonmin.algorithm=B-BB"]))
@variable(m, B[1:p])
@variable(m, G[1:p], Bin)
@variable(m, Z[1:p], Bin)
for i=1:p
    addSOS1(m, [B[i],Z[i]])
end
@constraint(m, Z .== 1 .-G )
@constraint(m, sum(G[j] for j=1:p) <= 3)
@NLobjective(m, Min, sum((Y[i]-sum( X[i,j]*B[j] for j=1:p))^2 for i=1:n))
solve(m)

```

---

<div class="post-metadata">

**Author:** ![leethargo](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/leethargo/32/6004_2.png) [@leethargo](https://discourse.julialang.org/u/leethargo)\
**Post date:** [August 18, 2017, 6:52pm UTC](https://discourse.julialang.org/t/sos1-constraints-in-bonmin-solver-jump-amplnlwriter/5450/2 "2017-08-18T18:52:37Z")

</div>

I’m just guessing, but maybe it works for Gurobi because it uses the `LinearQuadratic` interface, while AmplNLWriter uses the `Nonlinear` interface, where the latter does not know about SOS1 constraints.

---

<div class="post-metadata">

**Author:** ![michaellindon](https://avatars.discourse-cdn.com/v4/letter/m/da6949/32.png) [@michaellindon](https://discourse.julialang.org/u/michaellindon)\
**Post date:** [August 20, 2017, 9:04pm UTC](https://discourse.julialang.org/t/sos1-constraints-in-bonmin-solver-jump-amplnlwriter/5450/3 "2017-08-20T21:04:49Z")

</div>

Are there any work-arounds or alternatives I can use to solve minlp with sos constraints in julia?

---

<div class="post-metadata">

**Author:** ![michaellindon](https://avatars.discourse-cdn.com/v4/letter/m/da6949/32.png) [@michaellindon](https://discourse.julialang.org/u/michaellindon)\
**Post date:** [August 20, 2017, 10:00pm UTC](https://discourse.julialang.org/t/sos1-constraints-in-bonmin-solver-jump-amplnlwriter/5450/4 "2017-08-20T22:00:16Z")

</div>

I have tried a different route, using CoinOptServices.jl

```julia
using CoinOptservices
m = Model(solver=OsilBonminSolver())
@variable(m, B[1:p])
@variable(m, G[1:p], Bin)
@variable(m, Z[1:p], Bin)
for i=1:p
    addSOS1(m, [B[i],Z[i]])
end
@constraint(m, Z .== 1 .-G )
@constraint(m, sum(G[j] for j=1:p) <= 3)
@NLobjective(m, Min, sum((Y[i]-sum( X[i,j]*B[j] for j=1:p))^2 for i=1:n))

solve(m)

```

and get the same error

```julia

julia> solve(m)
ERROR: Not implemented for SOS constraints
Stacktrace:
 [1] constraintbounds(::JuMP.Model, ::JuMP.ProblemTraits) at /home/michael/.julia/v0.6/JuMP/src/solvers.jl:1033
 [2] _buildInternalModel_nlp(::JuMP.Model, ::JuMP.ProblemTraits) at /home/michael/.julia/v0.6/JuMP/src/nlp.jl:1243
 [3] #build#119(::Bool, ::Bool, ::JuMP.ProblemTraits, ::Function, ::JuMP.Model) at /home/michael/.julia/v0.6/JuMP/src/solvers.jl:303
 [4] (::JuMP.#kw##build)(::Array{Any,1}, ::JuMP.#build, ::JuMP.Model) at ./<missing>:0
 [5] #solve#116(::Bool, ::Bool, ::Bool, ::Array{Any,1}, ::Function, ::JuMP.Model) at /home/michael/.julia/v0.6/JuMP/src/solvers.jl:168
 [6] solve(::JuMP.Model) at /home/michael/.julia/v0.6/JuMP/src/solvers.jl:150
 [7] macro expansion at ./REPL.jl:97 [inlined]
 [8] (::Base.REPL.##1#2{Base.REPL.REPLBackend})() at ./event.jl:73

```

---

<div class="post-metadata">

**Author:** ![leethargo](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/leethargo/32/6004_2.png) [@leethargo](https://discourse.julialang.org/u/leethargo)\
**Post date:** [August 21, 2017, 6:10am UTC](https://discourse.julialang.org/t/sos1-constraints-in-bonmin-solver-jump-amplnlwriter/5450/5 "2017-08-21T06:10:08Z")

</div>

I feel like you will always run into the same problem: only the [LinearQuadratic interface](http://mathprogbasejl.readthedocs.io/en/latest/lpqcqp.html#addsos1!) supports SOS-type constraints.

In case you can derive some finite bounds for your `B` variables, you could just reformulate it as big-M type linear inequalities, right?

---

<div class="post-metadata">

**Author:** ![michaellindon](https://avatars.discourse-cdn.com/v4/letter/m/da6949/32.png) [@michaellindon](https://discourse.julialang.org/u/michaellindon)\
**Post date:** [August 21, 2017, 2:02pm UTC](https://discourse.julialang.org/t/sos1-constraints-in-bonmin-solver-jump-amplnlwriter/5450/6 "2017-08-21T14:02:31Z")

</div>

I do have a finite bound, however, the Big-M constraint isn’t as powerful I believe as the SOS1 constraint. Its my understanding that specifying an SOS1 constraint affects the branching procedure and results in a much faster algorithm than the Big-M.

---

<div class="post-metadata">

**Author:** ![miles.lubin](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/miles.lubin/32/279_2.png) [@miles.lubin](https://discourse.julialang.org/u/miles.lubin)\
**Post date:** [August 23, 2017, 11:24am UTC](https://discourse.julialang.org/t/sos1-constraints-in-bonmin-solver-jump-amplnlwriter/5450/7 "2017-08-23T11:24:07Z")

</div>

You’ll have to dig deeper and see precisely through what API interface Bonmin accepts SOS1 constraints. This doesn’t seem clear from the manual. After that, we can see how to pipe the constraints through from JuMP.

---

<div class="post-metadata">

**Author:** ![michaellindon](https://avatars.discourse-cdn.com/v4/letter/m/da6949/32.png) [@michaellindon](https://discourse.julialang.org/u/michaellindon)\
**Post date:** [August 23, 2017, 12:56pm UTC](https://discourse.julialang.org/t/sos1-constraints-in-bonmin-solver-jump-amplnlwriter/5450/8 "2017-08-23T12:56:27Z")

</div>

I believe it is with their B-BB branch and bound algorithm. Let me try and get an example using SOS constraints to run via AMPL using Bonmin as its solver and I will report back.
