baybe icon indicating copy to clipboard operation
baybe copied to clipboard

Refactor General Constraint Interface

Open dasmy opened this issue 1 year ago • 1 comments

The current interface for constraints is a bit inconvenient.

E.g., looking at

ContinuousLinearConstraint(parameters=["T1", "T2", "t1"], coefficients=[1.0, -1.0, max_temp_ramp_rate], operator=">=", rhs=0.0)

Why are parameters and coefficients given in separate lists? Wouldn't it be desirable to rather have a list of tuples, like

ContinuousLinearConstraint([ (1.0, "T1"), (-1.0, "T2"), (max_temp_ramp_rate, "t1"), (">=", 0.0) ])

This would enable for a much more natural reading order.

More suggestions:

  • Instead of / in addition to the parameter name strings, we could also accept everything derived from ContinuousParameter and pull the name property from that.
  • Would love to see constants for ">=", "<=", etc. and / or type annotations for static type checking.
  • Even further: We could overload *, +, -, etc. for the ContinousParameter class to yield a (multi)linear polynomial that - with properly overloaded <= and >= could directly yield a Constraint

dasmy avatar Mar 25 '25 17:03 dasmy

Hi @dasmy, I agree that many of the constraint classes deserve an overhaul in terms of their interface, which is sometimes really more complicated than necessary (there are more urgent cases than the ContinousLinearConstraint, in fact 🙃 ). Also, the constraints package is one of the parts where the typing/conversion/validation is not yet rock-solid, as you correctly pointed out. Happy to pull you into the discussion once we get to that, which could happen once the current wave of major upgrades is completed.

I also like your ideas (in fact, I've just recently implement similar things for our transformations), but I think each of them requires a detailed triage to figure out if it really improves the situation. In fact, I see potential difficulties for each of them that might not warrant the corresponding change. Most of them are subtle, but still.

To give just one example, your first one opens doors for this somewhat undefined situation:

p1_1 = NumericalContinuousParameter(name="p1", bounds=(0, 1))
p1_2 = NumericalContinuousParameter(name="p1", bounds=(-10, 10))
p2 = NumericalContinuousParameter(name="p2", bounds=(0, 1))
c = ContinuousLinearConstraint(
    parameters=[p1_1, p2],
    coefficients=[1.0, 1.0],
    operator=">=",
    rhs=0.0,
)
searchspace = SearchSpace.from_product([p1_2, p2], [c])

But let's first fix the basic interface before we think about the more advanced construction routes 😃

AdrianSosic avatar Mar 25 '25 20:03 AdrianSosic