Hello,
I’m trying to understand the values outputted when evaluating a constraint. In another thread I received this useful response on how to evaluate constraints. I’ll use a slightly modified example from there (pasted below) to illustrate my confusion:
Why does evaluating a constraint yield the left-hand side of the constraint? I expected that evaluating the constraint would give either A) a binary value indicating whether or not the constraint was satisfied or B) a continuous value indicating how far we are from satisfying the constraint.
Is there a way to extract values like A) or B) from the constraints without modifying the constraints themselves?
Concretely, for x = 0.3795
and the 2x <= 0.5
constraint, I would expect either A) 0 (or false) because the constraint isn’t satisfied or B) 0.25901
(which is 2x - 0.5
) and tells us how far we are from satisfying the constraint.
Concretely, for x = 0.3795
and the 0 <= sin(x) <= 0.5
constraint, I would expect either A) 1 (or true) because the constraint is satisfied or B) 0
indicating we need this much change (a.k.a. no change) to satisfy the constraint.
julia> using JuMP
julia> model = Model();
julia> @variable(model, x >= 0)
x
julia> @constraint(model, c, 2x <= 0.5)
c : 2 x ≤ 0.5
julia> @NLconstraint(model, nl_con, 0 <= sin(x) <= 0.5)
0 ≤ sin(x) ≤ 0.5
julia> variable_values = Dict(v => rand() for v in all_variables(model))
Dict{VariableRef, Float64} with 1 entry:
x => 0.379509
julia> cons = all_constraints(model; include_variable_in_set_constraints = true)
3-element Vector{ConstraintRef}:
c : 2 x ≤ 0.5
x ≥ 0.0
0 ≤ sin(x) ≤ 0.5
julia> sol = Dict(c => value(xi -> variable_values[xi], c) for c in cons)
Dict{ConstraintRef{Model, C, ScalarShape} where C, Float64} with 3 entries:
0 ≤ sin(x) ≤ 0.5 => 0.370465
x ≥ 0.0 => 0.379509
c : 2 x ≤ 0.5 => 0.759019
julia> sol[c]
0.759018812310488
julia> sol[nl_con]
0.37046482764020316
julia> sol[LowerBoundRef(x)]
0.379509406155244