Using JuMP
Since version 2.0.0, ClusteredLowRankSolver supports JuMP. Models should be created using
model = GenericModel{BigFloat}(ClusteredLowRankSolver.Optimizer)It is possible to round solutions from JuMP models using find_field and exact_solution. However, due to how JuMP is designed, the model will not be modified since the number type of the model cannot be changed to Nemo numbers. If no bridges are used (the model only uses PSD, nonnegative and free variables, and equality constraints), the variables in the Problem and PrimalSolution have the same names as the JuMP variables (where possible).
Below is the code for the Lovasz-theta number of the 5-cycle, modified from the JuMP documentation.
using ClusteredLowRankSolver, JuMP
function example_theta_problem()
# define the model
model = GenericModel{BigFloat}(ClusteredLowRankSolver.Optimizer)
# need precise enough solution for the rounding
set_attribute(model, "duality_gap_threshold", 1e-30)
# define the SDP
E = [(1, 2), (2, 3), (3, 4), (4, 5), (5, 1)]
@variable(model, X[1:5, 1:5], PSD)
for i in 1:5
for j in (i+1):5
if !((i, j) in E || (j, i) in E)
A = zeros(Int, 5, 5)
A[i, j] = 1
A[j, i] = 1
@constraint(model, LinearAlgebra.dot(A, X) == 0)
end
end
end
@constraint(model, LinearAlgebra.tr(LinearAlgebra.I * X) == 1)
J = ones(Int, 5, 5)
@objective(model, Max, LinearAlgebra.dot(J, X))
# solve the SDP
optimize!(model)
assert_is_solved_and_feasible(model)
println("The Lovász number is: $(objective_value(model))")
# round the solution
FF, g = find_field(model)
status, problem, esol = exact_solution(model; FF, g)
# problem and esol are the ClusteredLowRankSolver structs, so we can extract the matrix using
matrixvar(esol, :X)
# If bridges where used to transform the problem in a SDP in equality form,
# the names of the variables are indices (e.g. matrixvar(esol, 1))
println("The exact objective is $(objvalue(problem, esol)) with z approximately equal to $g")
return objvalue(problem, esol), g
end