Couenne

Convex Over and Under ENvelopes for Nonlinear Estimation - global optimizer for nonconvex MINLP

Layer 3

Couenne: Global Optimization for Nonconvex MINLP

Couenne (Convex Over and Under ENvelopes for Nonlinear Estimation) solves nonconvex mixed-integer nonlinear programs to global optimality. Unlike Bonmin (which assumes convexity), Couenne can prove that it has found the globally optimal solution even for nonconvex problems.

Layer 3 | 32 annotated files | Global Optimization


Problem Class

Couenne handles the most general class of MINLP:

$$\min_{x,y} \quad f(x, y)$$

Subject to: $$g(x, y) \leq 0$$ $$x \in \mathbb{R}^n, \quad y \in {0,1}^m$$

Where $f$ and $g$ can be nonconvex functions including:

Bonmin vs. Couenne: If your problem is convex, use Bonmin—it's faster. If your problem is nonconvex (or you don't know), use Couenne—it guarantees global optimality but takes longer.


Spatial Branch-and-Bound

Couenne extends branch-and-bound from integer variables to continuous domains:

Standard B&B:     Branch on integer variables
Spatial B&B:      Branch on continuous variables too

Why Branch on Continuous Variables?

For nonconvex functions, the convex relaxation may be weak:

                    True nonconvex function
                   /
    ┌─────────────●─────────────┐
    │            ╱ ╲            │
    │           ╱   ╲           │  ← Large gap between
    │──────────●─────●──────────│     function and envelope
    │         ╱       ╲         │
    │        ╱         ╲        │
    └───────●───────────●───────┘
            │           │
            lb          ub

By subdividing the domain [lb, ub] into smaller intervals, the convex envelope becomes tighter:

    ┌─────●─────┐     ┌─────●─────┐
    │    ╱╲     │     │    ╱╲     │
    │───●──●────│     │───●──●────│  ← Tighter envelopes
    │  ╱    ╲   │     │  ╱    ╲   │     on smaller domains
    │ ╱      ╲  │     │ ╱      ╲  │
    └●────────●─┘     └●────────●─┘
     lb    mid         mid    ub

Reformulation via Auxiliary Variables

Couenne transforms complex expressions into simple forms using auxiliary variables:

Standardization Process

Original: $\min f(g(h(x)))$

Reformulated: $$w_1 = h(x) \quad \text{(innermost)}$$ $$w_2 = g(w_1)$$ $$w_3 = f(w_2) \quad \text{(objective)}$$

Benefits of Reformulation

  1. Simpler convexification: Each $w_i = f_i(\ldots)$ is a simple expression with known convex envelope
  2. Structured propagation: Bound tightening through DAG is systematic
  3. Modular cuts: Add cuts for each simple relation independently

Expression Ranking

Variables are ranked by depth in the expression DAG:

rank(original_var) = 1
rank(w = f(x)) = rank(x) + 1
rank(w = f(x1,...,xk)) = 1 + max{rank(xi)}

Higher rank means deeper in DAG → branching has more propagation impact.


Bound Tightening Techniques

Couenne implements multiple bound tightening strategies:

Feasibility-Based Bound Tightening (FBBT)

Propagate bounds through expression DAG:

For $w = x \cdot y$ with $x \in [l_x, u_x]$, $y \in [l_y, u_y]$:

$$w^L = \min{l_x l_y, l_x u_y, u_x l_y, u_x u_y}$$ $$w^U = \max{l_x l_y, l_x u_y, u_x l_y, u_x u_y}$$

Optimization-Based Bound Tightening (OBBT)

Solve LPs to find tightest bounds:

$$x^L_i = \min x_i \quad \text{s.t. convex relaxation}$$ $$x^U_i = \max x_i \quad \text{s.t. convex relaxation}$$

Two-Implied Bound Tightening

Combine pairs of constraints for tighter bounds than single-constraint FBBT:

Example:

Single-constraint FBBT gives $x \geq 1$. Adding the constraints gives $2x \geq 3$, so $x \geq 1.5$.


Branching Strategies

Spatial Branching Objects

For auxiliary variable $w = f(x)$, infeasibility is:

$$\text{infeasibility}(w) = |w_{\text{current}} - f(x_{\text{current}})|$$

This measures the relaxation gap—how far the LP solution is from satisfying the true nonlinear constraint.

Branching Point Selection

StrategyDescriptionBest For
MID_INTERVAL$\alpha \cdot l + (1-\alpha) \cdot x^* + \alpha \cdot u$Safe default
MIN_AREAMinimize total envelope areaTight relaxations
LP_CENTRALBranch at LP solution $x^*$When LP is informative
LP_CLAMPEDLP solution clamped away from boundsAvoid tiny subproblems
BALANCEDBalance improvement on both branchesBalanced trees

Three-Way Branching

For some expressions, three-way branching is effective:


Convexification Cuts

Expression-Specific Envelopes

Each expression type has tailored convex relaxations:

ExpressionLower EnvelopeUpper Envelope
$x^2$Secant lineParabola itself (convex)
$xy$ (bilinear)McCormick underestimatorsMcCormick overestimators
$\log(x)$SecantTangent lines
$e^x$Tangent linesSecant

McCormick Envelopes for Bilinear Terms

For $w = xy$ with $x \in [l_x, u_x]$, $y \in [l_y, u_y]$:

Underestimators: $$w \geq l_x y + x l_y - l_x l_y$$ $$w \geq u_x y + x u_y - u_x u_y$$

Overestimators: $$w \leq u_x y + x l_y - u_x l_y$$ $$w \leq l_x y + x u_y - l_x u_y$$

Cross-Convexification

Exploits algebraic identities between auxiliary variables:

Example: If $w_3 = \log(x_1)$, $w_4 = \log(x_2)$, $w_5 = x_1 \cdot x_2$:

Then $w_3 + w_4 = \log(w_5)$ provides a valid cut from algebraic identity.


Key Components

Core Classes

ClassPurpose
CouenneProblemProblem representation with expression DAG
exprAuxAuxiliary variable $w = f(x)$
CouenneObjectBranching object for spatial B&B
CouenneChooseVariableVariable selection for branching

Bound Tightening

ClassDescription
CouenneFixPointFBBT through expression DAG
CouenneAggrProbingOBBT via LP optimization
CouenneTwoImpliedTwo-constraint implied bounds
CouenneMultiVarProbeMulti-variable probing

Cut Generators

ClassDescription
CouenneCutGeneratorMain convexification cuts
CouenneCrossConvCuts from algebraic identities
CouenneDisjCutsDisjunctive cuts

Heuristics

ClassDescription
BonNlpHeuristicNLP heuristic for feasible solutions
CouenneIterativeRoundingIterative rounding heuristic

Usage Example

#include "BonCouenneSetup.hpp"
#include "BonCbc.hpp"

// Couenne extends Bonmin's interface
int main() {
    Couenne::CouenneSetup couenne;
    couenne.InitializeCouenne();

    // Load problem (e.g., from AMPL .nl file)
    couenne.readProblem("problem.nl");

    // Configure spatial B&B
    couenne.options()->SetStringValue("branching_object", "expr_obj");
    couenne.options()->SetStringValue("branch_pt_select", "mid_interval");

    // Set bound tightening options
    couenne.options()->SetStringValue("feasibility_bt", "yes");
    couenne.options()->SetStringValue("optimality_bt", "yes");

    // Solve
    Bonmin::Bab bb;
    bb(couenne);

    // Global optimum found (if successful)
    if (bb.bestSolution()) {
        // Solution is provably globally optimal
    }
}

Source Files

Core Infrastructure

FileDescription
CouenneProblem.hpp Problem representation
CouenneExprAux.hpp Auxiliary variables
CouenneExpression.hpp Expression base class

Branching

FileDescription
CouenneObject.hpp Spatial branching objects
CouenneChooseVariable.hpp Variable selection
CouenneVarObject.hpp Variable-based branching

Bound Tightening

FileDescription
CouenneTwoImplied.hpp Two-constraint FBBT
CouenneMultiVarProbe.hpp Multi-variable probing

Cuts

FileDescription
CouenneCrossConv.hpp Cross-convexification cuts
CouenneDisjCuts.hpp Disjunctive cuts

Dependencies


Comparison: Convex vs. Global Optimization

AspectBonmin (Convex)Couenne (Global)
Problem classConvex MINLPAny MINLP
GuaranteeGlobal (by convexity)Global (proven)
RelaxationLP/NLPConvex envelope
BranchingInteger onlyInteger + continuous
SpeedFasterSlower
Typical useEngineering designProcess synthesis

References