Closed
Description
Hi,
it seems that deleting one constraint erases more information than it should.
Below is a MWE. With HiGHS everything runs as expected, but we get the following error with SCIP
Add equality constraint...
┌ Error: SCIP test failed with error:
│ exception =
│ KeyError: key MOI.VariableIndex(1) not found
│ Stacktrace:
│ [1] getindex(h::Dict{MathOptInterface.VariableIndex, MathOptInterface.Interval{Float64}}, key::MathOptInterface.VariableIndex)
│ @ Base ./dict.jl:477
│ [2] add_constraint(o::SCIP.Optimizer, vi::MathOptInterface.VariableIndex, set::MathOptInterface.EqualTo{Float64})
│ @ SCIP ~/.julia/packages/SCIP/1OzGv/src/MOI_wrapper/variable.jl:322
│ [3] build_and_modify_model(optimizer_constructor::Type{SCIP.Optimizer}, optimizer_name::String)
│ @ Main ~/Documents/research_projects/minimal_constraint_deletion_example.jl:55
│ [4] top-level scope
│ @ ~/Documents/research_projects/minimal_constraint_deletion_example.jl:77
│ [5] include(mod::Module, _path::String)
│ @ Base ./Base.jl:557
│ [6] exec_options(opts::Base.JLOptions)
│ @ Base ./client.jl:323
│ [7] _start()
│ @ Base ./client.jl:531
└ @ Main ~/Documents/research_projects/minimal_constraint_deletion_example.jl:80
while trying to add the equal to constraint.
For some background, we want to fix specific (less than, greater than) constraints to equality during the solve but they might not necessarily be bound constraints. Hence, we are reading out the function format instead creating a new function.
using MathOptInterface
using SCIP
using HiGHS
const MOI = MathOptInterface
function build_and_modify_model(optimizer_constructor, optimizer_name)
println("=" ^ 50)
println("Testing with $optimizer_name")
println("=" ^ 50)
# Build the model
o = optimizer_constructor()
MOI.set(o, MOI.Silent(), true)
MOI.empty!(o)
n = 3 # Number of variables
x = MOI.add_variables(o, n)
# Add constraints
greater_than_constraints = []
less_than_constraints = []
binary_constraints = []
for (i, xi) in enumerate(x)
# Add greater than constraint
gt_constraint = MOI.add_constraint(o, xi, MOI.GreaterThan(0.0))
push!(greater_than_constraints, gt_constraint)
# Add less than constraint
lt_constraint = MOI.add_constraint(o, xi, MOI.LessThan(1.0))
push!(less_than_constraints, lt_constraint)
# Add binary constraint
bin_constraint = MOI.add_constraint(o, xi, MOI.ZeroOne())
push!(binary_constraints, bin_constraint)
end
func = MOI.get(o, MOI.ConstraintFunction(), greater_than_constraints[1])
set = MOI.get(o, MOI.ConstraintSet(), greater_than_constraints[1])
println("Model after building:")
print(o)
# Delete the first greater than constraint
println("\nDeleting first less than constraint...")
MOI.delete(o, less_than_constraints[1])
println("\nDelete first greater than constraint...")
check_cidx = MOI.ConstraintIndex{MOI.VariableIndex,MOI.GreaterThan{Float64}}(greater_than_constraints[1].value)
MOI.delete(o, check_cidx)
println("\nAdd equality constraint...")
MOI.add_constraint(o, func, MOI.EqualTo(set.lower))
println("\nModel after adding equality constraint:")
print(o)
return o
end
# Test with HiGHS
println("Starting HiGHS test...")
try
o = build_and_modify_model(HiGHS.Optimizer, "HiGHS")
println("HiGHS test completed successfully!")
catch e
@error "HiGHS test failed with error:" exception=(e, catch_backtrace())
end
println("\n" * "=" ^ 80 * "\n")
# Test with SCIP
println("Starting SCIP test...")
try
o = build_and_modify_model(SCIP.Optimizer, "SCIP")
println("SCIP test completed successfully!")
catch e
@error "SCIP test failed with error:" exception=(e, catch_backtrace())
end