delta_moments.h#

#include <sif/model/delta_moments.h>
SIF_MODEL_DELTA_MOMENTS_H#

Spectral moments and the covariance of the smoothed field, evaluated from a tabulated power spectrum.

The modelled counterpart to the measured moments in measure/: same container, same window conventions, so a measurement and a prediction can be compared without converting between them.

Everything here quadratures the supplied table directly rather than interpolating it, so accuracy follows from how finely P(k) was sampled. See the note on sif_delta_covariance_pk() for what “finely” means.

SIF_COV_INDEX(i, j)#

Index of S(i, j) in a packed lower triangle, for j <= i.

Row-major over the lower triangle, in the ascending order of the radii.

SIF_COV_SIZE(n)#

Number of entries in a packed lower triangle of n rows.

sif_delta_moments_t *sif_delta_moments_pk(const sif_real *k, const sif_real *pk, uint32_t n_points, const sif_real *radii, uint32_t n_radii, uint8_t order, sif_option opt)#

Evaluates the spectral moments from a tabulated power spectrum.

Parameters:
  • k – Wavenumbers, strictly positive and strictly increasing

  • pk – Power spectrum sampled at k. Subtract any Poisson floor before calling; this takes the table as given.

  • n_points – Length of k and pk, at least 2

  • radii – Smoothing radii, strictly positive

  • n_radii – Number of radii

  • order – Highest moment order, at most SIF_MAX_MOMENT_ORDER

  • opt – SIF_DELTA_FILTER_*

Returns:

Newly allocated moment set, or NULL on invalid input or failure.

sif_real *sif_delta_sigma_slope_pk(const sif_real *k, const sif_real *pk, uint32_t n_points, const sif_real *radii, uint32_t n_radii, sif_option opt)#

Logarithmic slope dln(sigma)/dln(R) of the r.m.s. density contrast.

Evaluated by differentiating the window under the integral, so it is exact for the tabulated spectrum rather than a finite difference over radii: the radii need not be ordered, spaced, or numerous.

Parameters:
  • k – Wavenumbers, strictly positive and strictly increasing

  • pk – Power spectrum sampled at k

  • n_points – Length of k and pk, at least 2

  • radii – Smoothing radii, strictly positive

  • n_radii – Number of radii

  • opt – SIF_DELTA_FILTER_*

Returns:

Newly allocated array of n_radii slopes, negative where sigma falls with R, released with sif_free_aligned, or NULL on invalid input.

double *sif_delta_covariance_pk(const sif_real *k, const sif_real *pk, uint32_t n_points, const sif_real *radii, uint32_t n_radii, sif_real *sigma, sif_real *high_k_fraction, double *deriv_variance, sif_option opt)#

Covariance of the smoothed density field between every pair of smoothing radii.

S(R_i, R_j) = (1 / 2 pi^2) integral dk k^2 P(k) W(k R_i) W(k R_j)

Its diagonal is sigma_0^2(R), and reproduces sif_delta_moments_pk to rounding: both use the same window and the same trapezoid in log k.

Note

Quadratured directly, with no interpolation of P(k), so the accuracy is set by how finely the table is sampled rather than by an interpolant. The top-hat window oscillates as cos(kR) above kR ~ 1, and resolving that needs on the order of 1000 log-spaced points across the range where the integrand has support; 4000 over eleven decades leaves the residual below 1e-7. A coarse table will not be detected, it will simply be integrated badly.

Note

Accumulated as a Gram product, S = A A^T, so the result is positive semi-definite by construction for any non-negative P(k) – the property anything factorizing this matrix depends on.

Parameters:
  • k – Wavenumbers, strictly positive and strictly increasing

  • pk – Power spectrum sampled at k, non-negative at every point. Stricter than sif_delta_moments_pk, which never takes its square root.

  • n_points – Length of k and pk, at least 2; see the sampling note above

  • radii – Smoothing radii, strictly positive, at least 1 and at most SIF_COV_MAX_RADII. Packed in the order given; consumers generally require ascending.

  • n_radii – Number of radii

  • sigma – Optional output, n_radii entries: sqrt of the diagonal, and the sigma the field described by this covariance actually has. Pass NULL to skip.

  • high_k_fraction – Optional output, n_radii entries: the fraction of each diagonal element accumulated above half of k[n_points-1], as in sif_delta_moments_pk. Pass NULL to skip.

  • deriv_variance –

    Optional output, n_radii entries:

    <(d delta / dS)^2>, S = sigma^2(R)

the variance of the smoothed field’s derivative with respect to its own variance, which is the mixed second derivative of this covariance evaluated on its diagonal. Pass NULL to skip.

Note

Evaluated by differentiating the window under the integral, as sif_delta_sigma_slope_pk does, rather than by differencing the matrix. That is not a refinement: a finite difference of the diagonal converges only at second order in the radius spacing, so the value it returns depends on how finely the caller sampled radii – by around 3% at 100 radii and 8% at 50. Any consumer that treats this as a property of the field rather than of the grid needs the form computed here.

Note

Carries units of 1 / sigma^2. The dimensionless combination is 1 / (4 S <(d delta / dS)^2>), the squared correlation between the walk and its own derivative: zero for uncorrelated steps, one for a walk whose slope its value determines.

Note

Needs a longer and a finer k table than the covariance does. With a top-hat the integrand behind this output falls only as P(k) sin^2(kR), where the one behind the diagonal carries a further 1 / (kR)^4, so a table that gives a converged sigma can still be getting this badly wrong in two separate ways: stopping too low in k, and sampling too coarsely to resolve the oscillation, which needs k dlnk R < pi / 4 and so tightens with radius. A warning is emitted for each when more than a tenth of the integral is affected. high_k_fraction covers neither – it is a diagnostic for sigma.

Parameters:
  • opt – SIF_DELTA_FILTER_TOP_HAT (default) or SIF_DELTA_FILTER_GAUSSIAN

Returns:

Newly allocated packed lower triangle of SIF_COV_SIZE(n_radii) doubles, S(i, j) at SIF_COV_INDEX(i, j) for j <= i. Double rather than sif_real, since a single-precision factorization of a realistic radius grid reaches a non-positive pivot and fails. Released with sif_free_aligned, or NULL on invalid input.