Using QuadraticToBinary
QuadraticToBinary.jl is a package that converts quadratic terms in constraints and objective. To do so the pack acts like a solver on top of the real solver and most data is forwarded directly to the solver itself. For many solvers it is enough to use:
using BilevelJuMP, QuadraticToBinary, HiGHS
SOLVER = HiGHS.Optimizer()
Q_SOLVER = QuadraticToBinary.Optimizer{Float64}(SOLVER, lb = -10, ub = 10)
model = BilevelModel(()->Q_SOLVER, mode = BilevelJuMP.ProductMode(1e-6))
@variable(Lower(model), x)
@variable(Upper(model), y)
@objective(Upper(model), Min, 3x + y)
@constraints(Upper(model), begin
x <= 5
y <= 8
y >= 0
end)
@objective(Lower(model), Min, -x)
@constraints(Lower(model), begin
x + y <= 8
4x + y >= 8
2x + y <= 13
2x - 7y <= 0
end)
optimize!(model)
objective_value(model)
@assert abs(objective_value(model) - (3 * (3.5 * 8/15) + 8/15)) < 1e-1 # src
Running HiGHS 1.5.1 [date: 1970-01-01, git hash: 93f1876e4] Copyright (c) 2023 HiGHS under MIT licence terms Presolving model 383 rows, 224 cols, 1095 nonzeros 359 rows, 151 cols, 975 nonzeros 359 rows, 151 cols, 975 nonzeros Solving MIP model with: 359 rows 151 cols (27 binary, 0 integer, 0 implied int., 124 continuous) 975 nonzeros Nodes | B&B Tree | Objective Bounds | Dynamic Constraints | Work Proc. InQueue | Leaves Expl. | BestBound BestSol Gap | Cuts InLp Confl. | LpIters Time 0 0 0 0.00% 0 inf inf 0 0 0 0 0.0s 0 0 0 0.00% 6.133333333 inf inf 0 0 2 9 0.0s R 0 0 0 0.00% 6.133333333 6.160714286 0.44% 51 11 4 58 0.0s 25.9% inactive integer columns, restarting Solving report Status Optimal Primal bound 6.16071428571 Dual bound 6.16071428571 Gap 0% (tolerance: 0.01%) Solution status feasible 6.16071428571 (objective) 0 (bound viol.) 0 (int. viol.) 0 (row viol.) Timing 0.03 (total) 0.00 (presolve) 0.00 (postsolve) Nodes 0 LP iterations 400 (total) 0 (strong br.) 59 (separation) 322 (heuristics)
However, this might lead to some solver not supporting certain functionality like SCIP. In this case we need to:
using SCIP
SCIP requires a non-standard installation procedure in windows. See SCIP.jl for more details.
SOLVER = SCIP.Optimizer()
CACHED_SOLVER = MOI.Utilities.CachingOptimizer(
MOI.Utilities.UniversalFallback(MOI.Utilities.Model{Float64}()), SOLVER)
Q_SOLVER = QuadraticToBinary.Optimizer{Float64}(CACHED_SOLVER)
BilevelModel(()->Q_SOLVER, mode = BilevelJuMP.ProductMode(1e-5))
An Abstract JuMP Model Feasibility problem with: Variables: 0 Upper Constraints: 0 Lower Constraints: 0 Bilevel Model Solution method: BilevelJuMP.ProductMode{Float64}(1.0e-5, false, 0, nothing) Solver name: QuadraticToBinary [SCIP]
Note that we used ()->Q_SOLVER
instead of just Q_SOLVER
because BilevelModel
requires as constructor and not an instance of an object.
This page was generated using Literate.jl.