Mathematical programming / Linearization

Indicator Constraints

Express "if binary y = 1, then constraint C holds" natively, without hand-tuning a Big-M constant.

Note Intermediate

Short note. A compact reference, correct as far as it goes. It will be expanded into a full guide with a worked example and an interactive demonstration.

Problem

The Big-M method works, but picking M is fragile: too loose and the solver crawls, too tight and you cut off valid solutions. Modern solvers let you skip the constant entirely.

When to use it

Whenever your solver supports it (Gurobi, CPLEX, and modern OR-Tools CP-SAT all do) and the conditional relationship is a straightforward “if binary, then linear constraint.” It’s strictly better than Big-M when available.

Formulation

Conceptually identical to Big-M, but the solver enforces it directly during branch-and-bound rather than through a relaxed linear inequality:

y = 1  =>  a^T x <= b
y = 0  =>  no restriction on x

Code sketch

import gurobipy as gp
from gurobipy import GRB

model = gp.Model()
x = model.addVar(name="x")
y = model.addVar(vtype=GRB.BINARY, name="y")

# If y == 1, enforce x <= 500. No M needed.
model.addGenConstrIndicator(y, True, x <= 500)

Pitfalls

  • Indicator constraints are solved via branching, not the LP relaxation — they can still be slow on problems with many conditional rules. Profile before assuming they’re always faster than a well-tuned Big-M.
  • Not every open-source solver supports them. Check before committing — falling back to Big-M mid-project is annoying but not hard.
  • They express “if y, then constraint” cleanly, but for genuinely logical combinations (AND/OR/XOR across several binaries) see Logical Constraints.