mixle.analysis.sdm module¶
Species-distribution / habitat-suitability modelling (workstream N, N1; IC-12).
A presence-only species-distribution model (SDM) fit as an inhomogeneous Poisson point process (IPP)
over a discretised study area – the log-linear-intensity formulation that is mathematically equivalent
to MaxEnt (Renner & Warton, 2013). The study area is a grid of K cells with an environmental design
matrix X (+ intercept) and a per-cell area; presence detections are binned into per-cell counts
n_c exactly the way InhomogeneousPoissonProcessDistribution bins event times
into per-bin counts. The log-intensity log lambda_c = X_c @ beta is fit by maximizing the frozen
IPP log-likelihood (never reimplemented here – seq_log_density is called as the scorer) with a
ridge penalty and a log(area_c) offset; a Laplace approximation over beta is pushed forward
through the same log-link to give the fitted HabitatModel a full IC-1 Posterior surface over
the suitability field, with its variance recalibrated on a held-out fold via
mixle.analysis.kriging.calibrate_variance() so credible intervals hit their nominal coverage.
Presence-only bias (uneven survey effort) is corrected by an offset-based analogue of the Berman–Turner
background/thinning device: optional background quadrature points are binned the same way as
presences and folded into the per-cell offset as extra effective area, so cells with more background
sampling opportunity require proportionally more detections to imply the same fitted intensity – the fit
targets relative intensity rather than raw, effort-confounded detection counts.
- class SpeciesObservation(species_id, detection, location, crs=None, covariates=<factory>, modality='occurrence', provenance=<factory>)[source]
Bases:
objectOne presence/absence record for a species (an IC-4
Observationspecialisation).locationis the (already discretised) study-area coordinate: for a presence record consumed byfit_sdm(), the first component oflocationis the fractional cell index ([0, K)) on the same grid as thecovariates/cell_areapassed tofit_sdm– resolving a real-worldcrs-referenced location onto that grid is covariate/CRS ingest (B-series), out of scope here.
- class HabitatModel(beta, beta_cov, design, cell_area, *, species_id, var_scale=1.0, prior_dominated=False, provenance=None)[source]
Bases:
objectFitted IPP habitat-suitability field; satisfies IC-1
Posteriorover the suitability field.beta/beta_covare the Laplace-approximate posterior over the log-linear intensity coefficients;designis the(K, p)covariate design matrix (intercept + environmental covariates);cell_areais the per-cell area used as the Poisson offset during fitting. The suitability field is the fitted intensitylambda_c = exp(design_c @ beta)(mean);samples()/cov/credible_interval()push the beta-posterior forward through the same log-link (a delta-method / lognormal approximation), scaled by a held-out-calibrated variance multiplier, so every downstream consumer (N2’s no-mine mask, N4’s resistance raster) sees one calibrated field posterior.species_idis required (MXR-080-1590): a suitability field is a statement about ONE species, and a model with no identity on it cannot be checked against the species whose legal exclusion it is being used to impose (MXR-080-1591) or traced back to the dataset it was fitted from.provenancecarries immutable input receipts (fit_sdm()fills in the occurrence, background, covariate and cell-area digests) so a published field can be tied to its source data.- Parameters:
- samples(n, rng)[source]
Draw
nintensity-field realisations by pushingbetadraws throughexp(X @ beta).- Returns:
(n, K)array of intensity-field draws.- Raises:
ValueError –
nis not a positive exact integer (MXR-080-0114).- Parameters:
- Return type:
- property mean: ndarray
Fitted intensity field
lambda_c = exp(design_c @ beta)– the suitability surface.Uses the same overflow-safe
expas fitting (MXR-080-0114): a linear predictor that never overflowed under the training-time clip can still overflow plainexp()at a different design row (e.g. an extrapolated covariate) or for a directly-constructed model.
- property cov: ndarray | LinearOperator
Delta-method covariance of the intensity field, recalibrated.
Domains with at most 2,048 cells return a dense
(K, K)array. Larger domains return a symmetricLinearOperatorbacked by the(K, p)intensity Jacobian and(p, p)coefficient covariance, avoiding quadratic field storage.- Raises:
ValueError – the Jacobian or requested covariance operation is not finite. In particular, finite model inputs can still imply a covariance outside float64’s representable range; such a matrix is not published as posterior evidence.
- credible_interval(level)[source]
Per-cell central credible interval of the suitability field (lognormal delta-method).
- Raises:
ValueError –
levelis not finite and strictly in(0, 1)(MXR-080-0114).- Parameters:
level (float)
- Return type:
- derived_quantity(fn, n, rng)[source]
Pushforward
fnovernintensity-field draws into aDerivedQuantity(IC-1).
- fit_sdm(occurrences, covariates, cell_area, *, species_id, background=None, ridge=1e-3)[source]
Fit a presence-only habitat-suitability model as an inhomogeneous-Poisson point process.
Discretizes the study area into
K = covariates.shape[0]cells, binsoccurrences(onlydetection=Truerecords) into per-cell presence counts, and fits a log-linear intensitylog lambda_c = [1, covariates_c] @ betaby maximizing the frozen IPP log-likelihood with aridge * ||beta||^2penalty and alog(area_c)offset (Poisson GLM equivalent to MaxEnt). Ifbackgroundquadrature points are given, they are binned the same way and folded into the offset as extra effective area (an effort/thinning correction for presence-only sampling bias). The returnedHabitatModel’s field variance is recalibrated on an internal held-out cell fold viamixle.analysis.kriging.calibrate_variance()so its credible intervals hit their nominal (90%) coverage.species_idnames the ONE species being modelled and is required (MXR-080-1590). Everyoccurrencesrecord must carry that same id: the fit used to bin every truthy detection regardless of which species it belonged to, so a single fitted intensity could silently pool records from unrelated species into one field that claimed to describe all of them. The id is carried onto the returned model, together with immutable input digests inprovenance, so a published scientific result can be traced back to the exact dataset it came from and so a downstream legal exclusion can check the field it is applying actually belongs to the species it is applying it for (MXR-080-1591).- Parameters:
occurrences (list[SpeciesObservation]) – presence records for
species_id; eachlocation’s first component is the fractional cell index. A record for any other species is rejected, not silently pooled.covariates (ndarray) –
(K, p - 1)environmental covariates per cell (an intercept column is prepended).cell_area (ndarray) –
(K,)per-cell area (the Poisson offset).species_id (str) – the species this field is being fitted for.
background (ndarray | None) – optional quadrature/background point locations (same cell-index convention as
occurrences), used to correct for uneven survey effort.ridge (float) – L2 penalty strength on
beta(also regularizes the Laplace covariance).
- Returns:
A fitted
HabitatModelcarryingspecies_idand input receipts inprovenance.- Raises:
ValueError –
ridgeis not finite and non-negative;covariatesis not finite;cell_areadoes not have exactly one finite, strictly positive entry per covariate row; any presence or background location is non-finite or outside the cell-index domain[0, K)(MXR-080-0111);species_idis not a non-empty string or any occurrence record names a different species (MXR-080-1590); or the internal beta fit does not converge to finite coefficients (MXR-080-0113).- Return type:
HabitatModel