Skip to content

Constraint API Reference

Constraint

Constraint relating expressions with comparison operators and right-hand sides.

A constraint specifies a relationship between a left-hand side expression and a right-hand side value using a comparison operator (==, <=, >=). Constraints are typically created using comparison operators on expressions or variables.

Parameters:

  • lhs (Variable or Expression) –

    The left-hand side of the constraint.

  • rhs (float or Expression or Variable) –

    The right-hand side of the constraint.

  • comparator (Comparator) –

    The comparison operator (EQ, LE, or GE).

  • name (str, default: None ) –

    An optional name for the constraint for easier identification.

Attributes:

  • name (str) –

    The name of the constraint.

  • lhs (Expression) –

    The left-hand side expression (constant is moved to rhs).

  • rhs (float) –

    The right-hand side value (expressions and variables are moved to lhs).

  • comparator (Comparator) –

    The comparison operator.

Examples:

Create constraints using comparison operators (auto-assigned name):

>>> from luna_model import Variable, Environment
>>> with Environment():
...     x = Variable("x")
...     y = Variable("y")
>>> c1 = x + y <= 10
>>> c2 = 2 * x - y == 5
>>> c3 = x >= 0

Create named constraint:

>>> from luna_model.constraint import Constraint, Comparator
>>> with Environment():
...     x = Variable("x")
...     y = Variable("y")
>>> constraint = Constraint(x + y, 10, Comparator.LE, name="capacity")
Notes

The right-hand side is always normalized to a constant. If an expression or variable is provided as the right-hand side, it is moved to the left-hand side. If the left-hand side contains a non-zero constant value it is moved to the right-hand side.

name: str property writable

Get the constraint's name.

Returns:

  • str

    The constraint name.

lhs: Expression property

Get the left-hand side expression.

Returns:

rhs: float property

Get the right-hand side value.

Returns:

  • float

    The right-hand side constant value.

comparator: Comparator property

Get the comparison operator.

Returns:

  • Comparator

    The comparison operator (EQ, LE, or GE).

equal_contents(other: Constraint) -> bool

Check if two constraints have equal content.

Parameters:

  • other (Constraint) –

    The constraint to compare with.

Returns:

  • bool

    True if constraints have the same rhs, and comparator and the lhs has the same contents.

__eq__(other: Constraint) -> bool

Check if two constraints are exactly equal.

Parameters:

  • other (Constraint) –

    The constraint to compare with.

Returns:

  • bool

    True if constraints are structurally identical.

__str__() -> str

Return human-readable string representation.

Returns:

  • str

    String representation of the constraint.

__repr__() -> str

Return detailed string representation.

Returns:

  • str

    Detailed representation of the constraint.

Comparator

Bases: Enum

Comparison operators for constraints.

Defines the type of comparison used in a constraint between the left-hand side expression and the right-hand side value.

Attributes:

  • EQ (str) –

    Equality constraint (==). Requires lhs to equal rhs.

  • LE (str) –

    Less-than-or-equal constraint (<=). Requires lhs to be at most rhs.

  • GE (str) –

    Greater-than-or-equal constraint (>=). Requires lhs to be at least rhs.

Examples:

Comparators are typically created automatically through operator overloading:

>>> from luna_model import Variable, Environment
>>> with Environment():
...     x = Variable("x")
...     c1 = x == 1  # Creates EQ constraint
...     c2 = x <= 5  # Creates LE constraint
...     c3 = x >= 0  # Creates GE constraint
Notes

Strict inequality (<, >) is not supported in optimization constraints.

ConstraintCollection

Collection for managing multiple constraints.

A ConstraintCollection stores named constraints and provides methods for adding, retrieving, and iterating over constraints.

Attributes:

  • None directly exposed. Access constraints via indexing or iteration.

Examples:

Create and manage constraints:

>>> from luna_model import Variable, Environment
>>> from luna_model import ConstraintCollection
>>> with Environment():
...     x, y = Variable("x"), Variable("y")
>>> cc = ConstraintCollection()
>>> cc += x + y <= 10, "capacity"
>>> cc += x >= 0, "x_lower"
>>> print(len(cc))  # Number of constraints
2
>>> constraint = cc["capacity"]  # Access by name

Iterate over constraints:

>>> for name, constr in cc:
...     print(f"{name}: {constr}")
capacity: x + y <= 10
x_lower: x >= 0
Notes

Constraints are stored with unique string names. Adding a constraint with an existing name will raise a DuplicateConstraintNameError.

__init__() -> None

Initialize an empty constraint collection.

add_constraint(constraint: Constraint, name: str | None = None) -> None

Add a constraint to the collection.

Parameters:

  • constraint (Constraint) –

    The constraint to add.

  • name (str, default: None ) –

    Name for the constraint. If None, uses constraint's own name if it has one that is not auto-generated, otherwise generates a name following the pattern c{i} where i is the constraint's index in the collection (starting from 0).

add_constraints(constraints: ConstraintCollection | NDArray | NDLmArray | Sequence[Constraint] | Sequence[Constraint | tuple[str, Constraint] | tuple[Constraint, str]], name: str | Sequence[str] | None = None) -> list[str]

add_constraints(constraints: ConstraintCollection | Sequence[Constraint | tuple[str, Constraint] | tuple[Constraint, str]], name: str | None = None) -> list[str]
add_constraints(constraints: NDArray | NDLmArray | Sequence[Constraint], name: str | Sequence[str] | None = None) -> list[str]

Add multiple constraints to the collection.

Parameters:

  • constraints (ConstraintCollection | NDArray | NDLmArray | Sequence[Constraint]) –
            | Sequence[Constraint | tuple[str, Constraint] | tuple[Constraint, str]]
    

    Constraints to add.

    Behavior depends on the input kind:

    • ConstraintCollection: imports the full collection.
    • NDArray / NDLmArray / Sequence[Constraint]: each element is added as one constraint.
    • Sequence[Constraint | tuple[str, Constraint] | tuple[Constraint, str]]: each tuple provides an explicit per-constraint name.
  • name (str | Sequence[str] | None, default: None ) –

    Naming mode for added constraints:

    • None: use explicit tuple names when present; otherwise use each constraint's own non-auto-generated name, falling back to generated names.
    • str: use as a base prefix. For plain sequences/arrays names are {name}_{i}. For tuple inputs names are {name}_{tuple_name} when a tuple name is present, otherwise {name}_{i}.
    • Sequence[str]: allowed only with NDArray, NDLmArray, or Sequence[Constraint] and must have the same length as constraints.

Returns:

  • list[str]

    The names of the added constraints.

Raises:

  • DuplicateConstraintNameError

    If a constraint with the same name already exists.

  • IllegalConstraintNameError

    If the constraint name is invalid. Constraint names cannot be empty strings and must start with an alphabetical character. Additionally, constraint names cannot start with inf or nan due to limitations of other modeling software.

  • LunaModelError

    If name is a sequence and its length does not match the number of constraints. Also raised for unsupported combinations when runtime type checks are bypassed (for example, ConstraintCollection with Sequence[str] names).

items() -> ConstraintCollectionIter

Get an iterator over (name, constraint) pairs.

Returns:

encode() -> bytes

Encode the constraint collection to bytes.

Returns:

  • bytes

    Encoded constraint collection.

serialize() -> bytes

Serialize the constraint collection to bytes.

Returns:

  • bytes

    Serialized constraint collection.

get(name: str) -> Constraint

Get a constraint by its name.

Parameters:

  • name (str) –

    The name of the constraint.

Returns:

  • Constraint

    The constraint with the given name.

Raises:

  • NoConstraintForKeyError

    If no constraint with the given name exists.

remove(name: str) -> None

Remove a constraint by its name.

Parameters:

  • name (str) –

    The name of the constraint to remove.

Raises:

  • KeyError

    If no constraint with the given name exists.

equal_contents(other: ConstraintCollection) -> bool

Check if two constraint collections have the same contents.

Parameters:

Returns:

  • bool

    True if both collections contain the same constraints.

ctypes() -> list[Comparator]

Get the comparator types of all constraints.

Returns:

decode(data: bytes, env: Environment) -> ConstraintCollection classmethod

Decode into a ConstraintCollection based on the bytes data given an environment. Same as deserialize.

deserialize(data: bytes, env: Environment) -> ConstraintCollection classmethod

Deserialize into a ConstraintCollection based on the bytes data given an environment.

__iadd__(other: SingleConstraint | ManyConstraint | ConstraintCollection | tuple[ConstraintCollection, str]) -> Self

Add a constraint using += operator.

Parameters:

  • other (SingleConstraint | ManyConstraint | ConstraintCollection | tuple[ConstraintCollection, str]) –

    Either a Constraint, a (Constraint, name) tuple, a ConstraintCollection, a (ConstraintCollection, prefix) tuple, a sequence of either Constraint or (Constraint, str) or a (Sequence[Constraint], base_name) tuple.

    The constraint names of the added Constraint, ConstraintCollection or Sequence have to be different from this collection's constraint names. Otherwise the DuplicateConstraintNameError is raised.

Returns:

  • Self

    The collection itself for chaining.

Raises:

  • DuplicateConstraintNameError

    If a constraint is added for a name that is already contained in this collection. Or if a ConstraintCollection is added containing a constraint with a name that is already in this collection. Or if a Sequence is added containing a constraint with a name that is already in this collection.

__getitem__(key: str) -> Constraint

Get a constraint by name using indexing.

Parameters:

  • key (str) –

    The constraint name.

Returns:

  • Constraint

    The constraint with the given name.

__setitem__(key: str, value: Constraint) -> None

Set a constraint by name using indexing.

Parameters:

  • key (str) –

    The constraint name.

  • value (Constraint) –

    The constraint to store.

__len__() -> int

Get the number of constraints in the collection.

Returns:

  • int

    The number of constraints.

__eq__(other: ConstraintCollection) -> bool

Compare for equality.

__iter__() -> ConstraintCollectionIter

Iterate over (name, constraint) pairs.

Returns:

__hash__() -> int

Compute hash.

__str__() -> str

Return human-readable string representation.

Returns:

  • str

    String representation of the constraint collection.

ConstraintCollectionIter

Iterator for traversing constraint collections.

Yields (name, constraint) tuples when iterating over a ConstraintCollection.

Examples:

>>> from luna_model import Variable, Environment
>>> from luna_model import ConstraintCollection
>>> with Environment():
...     x, y = Variable("x"), Variable("y")
>>> cc = ConstraintCollection()
>>> cc += x + y <= 10, "capacity"
>>> cc += x >= 0, "x_lower"
>>> for name, constraint in cc:
...     print(f"{name}: {constraint}")
capacity: x + y <= 10
x_lower: x >= 0

__next__() -> tuple[str, Constraint]

Get the next (name, constraint) pair.

Returns:

Raises:

__iter__() -> ConstraintCollectionIter

Return the iterator object itself.