_means#

cultivars.engine._internals._means = <module 'cultivars.engine._internals._means' from '/home/runner/work/cultivars/cultivars/src/cultivars/engine/_internals/_means.py'>[source]#

how a conditional-variance model turns a draw into residuals.

A conditional-variance likelihood needs exactly three things from the mean specification – how many parameters it consumes, what residuals a given draw implies, and where to start the search. Everything else about the variance families is indifferent to whether that mean is a regression on lags or a recursion with a moving-average block.

Factoring those three out is what lets one variance objective serve both. Before this split, the objective held a design matrix and formed residuals as target - design @ mean, which silently assumed the mean was linear in observables – true for a constant and for pure autoregressive lags, false the moment a moving-average term appears, because a lagged residual is not a column you can build in advance. Adding an MA block by widening the design was never an option; it needed a different residual map, which is precisely what a layer is.

Two layers cover the group:

  1. _LinearMean is the regression case. Residuals come from one matrix product and the coefficients are unconstrained, since a mean that is estimated jointly with a variance does not need its autoregressive roots pinned inside the unit circle for the recursion to be evaluable.

  2. _ArmaMean is the recursion case. Residuals are produced one period at a time, so an explosive draw would feed itself and overflow – which is why this layer reparameterizes both blocks through the partial autocorrelations. Stationarity and invertibility then hold by construction and the optimizer searches an unconstrained space.

The layer owns its target rather than receiving it. An autoregressive-moving- average residual recursion reads levels from before the first modelled observation, so it needs the untrimmed series; handing it only the trimmed target and asking for residuals would either lose those lags or require the caller to know the trim, and the caller is the one place that should not have to.

Type:

Mean layers