Date:

2026

eindir Documentation

eindir

Overview

eindir ships typed primitives for ND objective functions and bounded sampling. It provides the Objective trait (and Python/C/C++ bindings), low-discrepancy point sets, bounds handling, a GLE coloured-noise thermostat with optimal-sampling drift, and surrogate infrastructure (Additive/Chebyshev/Reduced objectives). The Python surface is the familiar legacy API; the Rust eindir-core crate (with pyo3 + cbindgen) powers everything and is consumed by anneal for the five-component algebra.

Every primitive is designed for reuse: the same Objective and low-discrepancy facilities feed GLE, surrogates, QMC polish, and the anneal drivers without duplication. Use eindir directly when the task is to define an objective, generate bounded point sets, expose gradients across language boundaries, or build proposal machinery that should remain independent of a particular optimiser.

Key Features

Objective trait + bindings

ND f: R^D -> R with bounds, gradients (optional), and Python (pyo3 + array-api), C, C++ surfaces.

Builtin test objectives (Rastrigin, Rosenbrock, Styblinski-Tang, Ackley).

Low-discrepancy & halton

Bounded QMC point sets (Halton-based) for initialisation, pilots, polish, and surrogates.

The same deterministic sequence can seed starts, fit surrogates, or feed an optimiser, so benchmark campaigns do not mix sampling changes with algorithm changes.

GLE thermostat

Coloured-noise generalised Langevin (Ceriotti-Bussi-Parrinello) with optimal-sampling drift matrix.

BAB integrator, stationary reseed, exact small-matrix exp + LDL^T sqrt. The drift and covariance machinery provide reusable coloured-noise moves for objectives whose curvature spans separated time scales.

Surrogates

Additive (rank-1 separable Chebyshev) and total-degree Chebyshev surrogates, ReducedObjective (active subspace + surrogate).

These give downstream optimisers cheap structure without replacing the authoritative objective.

Python / C / C++ ABI

Mixed maturin layout for Python, cargo-c for C, hand-written C++ header.

Full interop with array API, DLPack, TVM-FFI in downstream (anneal).

Reuse with anneal

The same primitives power the typed SA algebra, Bayesian pilot/mixer, GLE-Langevin driver, QMC polish, device/ensemble backends, and surrogate independence proposals.

See the architecture page for the crate layout and the primitives explanation for the trait design. The IISE manuscript (HaoZeke/anneal) shows how these feed the five-component algebra.

What to Read First

  • Quickstart shows the smallest objective and bounded sampling workflow.

  • Using with anneal explains the division between primitives and search drivers.

  • Gradients covers the optional derivative path used by GLE and local polish.

  • API primitives names the stable concepts.

  • The generated Rust API starts at Rust API Reference and follows the eindir-core crate modules.

Background

eindir is the primitives layer of the simmAnneal stack. The companion package anneal consumes the Objective trait and ships the typed component algebra for simulated annealing (Obj/Cool/Neigh/Move/Accept + L1-L4 laws).

This crate hosts the core traits and helpers (Objective, low_disc, GLE, surrogates) plus the Python/C/C++ bindings. The IISE manuscript at HaoZeke/anneal defines the algebra that sits on top; the primitives here are deliberately reusable so the same low-discrepancy design, GLE drift, or surrogate can serve classical SA, HMC, polish, device backends, and surrogate proposals without reimplementation.