fips.Covariance.sample#
- Covariance.sample(rng=None)[source]#
Return one draw from \(N(0, S)\), a vector on the covariance’s space.
The draw is \(R w\) with \(R R^T = S\) and \(w\) standard normal, and \(R\) is the root the form makes cheapest, never the
n x nmatrix where the form is cheaper than that. A diagonal covariance scales its normals by the standard deviations; a block diagonal one draws each block in turn; a Kronecker one applies the Cholesky factors of its factors to normals on the whole product grid and keeps its rows (a part of a Gaussian vector has the part of its covariance), so a subset of the grid costs what the whole grid does; a sparse one draws each group of correlated rows (awithin=kernel’s site-days) from the Cholesky factor of its own block; a dense one uses its Cholesky factor. The root is built once and kept, so a loop of draws factors once: byCovariance(...), whose positive semidefinite check it is, or by the first draw of a covariance fips built from a model.A semi-definite covariance, a
Constant()kernel’s rank-one block for one, has no Cholesky factor, so it is drawn from its eigendecomposition, with the eigenvalues that are negative by roundoff set to zero and one INFO line logged.- Parameters:
rng (
int|Generator|None) – A seed, or the generator to draw from (used as given, so one generator passed to every call gives independent draws). None draws from fresh entropy. It goes throughnumpy.random.default_rng(), as SciPy’srngargument does. The same seed gives the same draw for the same form of covariance; a Kronecker covariance on a subset of its grid uses one normal for each point of the whole grid, so changing a covariance’s form changes the draw.- Returns:
The draw, on the covariance’s space.
- Return type:
- Raises:
numpy.linalg.LinAlgError – If the covariance has a clearly negative eigenvalue (not positive semi-definite).
See also
sqrtThe root \(L\), as an operator.
Examples
>>> import pandas as pd >>> from fips import Covariance, Space >>> space = Space({"flux": pd.Index(["a", "b", "c"], name="cell")}) >>> S = Covariance.diagonal([4.0, 1.0, 0.25], space) >>> S.sample(rng=0).to_series().round(2) block cell flux a 0.25 b -0.13 c 0.32 dtype: float64 >>> S.sample(rng=0).values.tolist() == S.sample(rng=0).values.tolist() True