Skip to main content

Model

Trait Model 

Source
pub trait Model: Send + Sync {
    // Required methods
    fn eval(&self, x: &[f64], params: &[f64]) -> f64;
    fn param_names(&self) -> Vec<Cow<'static, str>>;

    // Provided methods
    fn jacobian(&self, x: &[f64], params: &[f64]) -> Vec<f64> { ... }
    fn jacobian_into(&self, x: &[f64], params: &[f64], out: &mut [f64]) { ... }
    fn eval_slice_into(&self, xs: &[f64], params: &[f64], out: &mut [f64]) { ... }
    fn jac_slice_into(&self, xs: &[f64], params: &[f64], out: &mut [f64]) { ... }
    fn n_dims(&self) -> usize { ... }
}
Expand description

Core model trait implemented by every built-in kernel.

Convention: x is a coordinate slice.

  • 1-D models expect x.len() == 1 (i.e. x[0] is the scalar coordinate).
  • n-D models declare n_dims() > 1.

Required Methods§

Source

fn eval(&self, x: &[f64], params: &[f64]) -> f64

Evaluate the model at coordinate x with the given params.

§Preconditions

Implementations index params and x by raw position and assume the caller has already validated arity (this keeps the per-point evaluation branch-free on the hot path). The caller MUST guarantee:

  • params.len() == self.param_names().len()
  • x.len() >= self.n_dims()
§Panics

Panics (index-out-of-bounds) if params.len() < self.param_names().len() or x.len() < self.n_dims(). Because the pyo3 binding crate calls these kernels on the hot path, a panic here would unwind across the FFI boundary — validate param/coordinate arity at graph-compile time so the kernel is only ever invoked well-formed.

Source

fn param_names(&self) -> Vec<Cow<'static, str>>

Ordered parameter names, matching the layout expected by eval and jacobian.

Returns an owned Vec of Cow<'static, str> so that runtime-generated models (e.g. GaussianND{d} with dynamic center_0..center_{d-1}) can produce their parameter names without requiring compile-time-static slices. For all built-in kernels with static names, every element is Cow::Borrowed(&'static str) — zero extra heap allocation.

Provided Methods§

Source

fn jacobian(&self, x: &[f64], params: &[f64]) -> Vec<f64>

Jacobian — one derivative per parameter, in the same order as param_names().

The default implementation uses forward-difference finite differences with step h = 1e-7 * |p[i]|.max(1e-7) (relative + absolute floor). Override with an analytical formula when possible for best performance.

§Preconditions / Panics

Same arity contract as eval: the caller MUST ensure params.len() == self.param_names().len() and x.len() >= self.n_dims(). A short slice panics with an index-out-of-bounds rather than returning an error; the same FFI-unwind hazard applies, so validate arity upstream.

Source

fn jacobian_into(&self, x: &[f64], params: &[f64], out: &mut [f64])

Fill a pre-allocated slice with Jacobian values (one entry per parameter).

This is the hot-path companion to [jacobian]. The caller provides a scratch buffer (out) of length ≥ param_names().len(); the method writes derivatives into out[0..n_params] without any heap allocation.

The default falls back to [jacobian] and copies the result. Models with analytical Jacobians should override this to compute values directly into out, sharing intermediate calculations across parameters.

Source

fn eval_slice_into(&self, xs: &[f64], params: &[f64], out: &mut [f64])

Batch evaluation of a 1-D model: fill out[i] = eval([xs[i]], params).

Only called when n_dims() == 1.

Default: per-point loop calling eval(). Override to hoist loop-invariant constants (e.g. precompute 1/(2σ²) once) and let LLVM eliminate redundant arithmetic across the slice.

Source

fn jac_slice_into(&self, xs: &[f64], params: &[f64], out: &mut [f64])

Batch Jacobian for a 1-D model: fill out in row-major layout [i * params.len() + j] = d(model)/d(params[j]) at xs[i].

Only called when n_dims() == 1.

Default: per-point loop calling jacobian_into(). Override to hoist invariants (avoids recomputing σ² and the exp() argument for every point call).

Source

fn n_dims(&self) -> usize

Number of coordinate dimensions consumed from x. Defaults to 1.

Dyn Compatibility§

This trait is dyn compatible.

In older versions of Rust, dyn compatibility was called "object safety".

Implementors§