Relaxation of MIP to LP, getdual, CPLEX

question

#1

Hi guys.
I’ve been reading this forum and the previous one (on Google) and I can’t seem to find an answer (although there are close examples) to my problem.

It is about getting dual values out of an MIP. The standard way I know is solving the MIP, relax the problem and fix all the integer variables to their results from the MIP. Then solve the resulting LP and get the duals.

I’ve been trying to do this through the following small example:

using JuMP
using CPLEX

model = Model(solver=CplexSolver())

@variable(model, x >= 0)
@variable(model, y, Bin)

@constraint(model, cop, x + y>= 1.33)
@constraint(model, cop2, x <= 0.5 )
@objective(model, Min, x+2y)

println(model)

status = solve(model)

println(getobjectivevalue(model))
println("x: ", getvalue(x))
println("y: ", getvalue(y))
println("dual: ", getdual(cop))

println("============================")

setcategory(y, :Cont)
println(model)

status = solve(model)

println(getobjectivevalue(model))
println("x: ", getvalue(x))
println("y: ", getvalue(y))
println("dual: ", getdual(cop))

As expected, the first attempt to print the dual throws a warning, because the dual is not available and getdual(cop) returns a NaN. The problem is that the same happens on the second attempt, even when the model looks like:

Min x + 2 y
Subject to
x + y ≥ 1.33
x ≤ 0.5
x ≥ 0
0 ≤ y ≤ 1

I have tried using the following, with no luck.

status = solve(model, relaxation=true)

CPLEX throws a

CPLEX Error 1017: Not available for mixed-integer problems

even when no duals are requested, only because either

relaxation=true

or

setcategory(y, :Cont)

are on. I haven’t tried other solvers at this point. For the sake of performance and conciseness I’m trying to avoid rebuilding the whole model with only continuous variables.

Anybody knows how the query to CPLEX is being done? Maybe there is a header or something that stays fixed to command mipopt instead of optimize. Well, any advise is very welcome.

Cheers


#2

It’s possible that there is some bad state being maintained somewhere in CPLEX.jl (PRs accepted). As a workaround, you can call setsolver(model, CplexSolver()) to force JuMP to throw out the in-memory model and build a new one from scratch.


#3

It’s actually a little complicated. CPLEX maintains a problem type that is independent of the variable types.