rerrorV
Description
rerrorV is a random number generator (RNG) that generates random error from a population with and , and with user-defined amounts of skewness and (excess) kurtosis. It uses the Fleishman power method to achieve this.
This function uses RANDARRAY as its core RNG rather than the CLS-Stats version runif. This has three consequences:
- the output of
rerrorVis volatile rerrorVcannot be seeded- the quality of the RNG is a little better
Basically: use rerrorV if the stakes are higher (eg for a research publication).
Syntax
The same syntax as rerror but without the possibility of a seed: rerrorV(rows, cols, skew, kurt). See the documentation of rerror for constraints on skew and kurt inputs.
The output of rerrorV is volatile and slightly better quality than rerror. See the documentation of rerror for an example of its usage.
Source Code
Helpers used: FSolve, FSolveBump, FSolveLadder, FSolveMonotonic
rerrorV = LAMBDA(
[rows], [cols], // size of matrix returned (default of 1 for both)
[skew], [kurt], // desired skewness and excess kurtosis (default 0 for both)
LET(
// default values
rows, IF(ISOMITTED(rows), 1, rows),
cols, IF(ISOMITTED(cols), 1, cols),
skew, IF(ISOMITTED(skew), 0, skew),
// do not allow kurtosis below minimum or below zero
kmin, MAX(0, Fkmin(skew)),
// error if the user explicitly asked for a kurtosis below the feasible minimum
kurtTooSmall, IF(ISOMITTED(kurt), FALSE, kurt < kmin),
kurt, IF(ISOMITTED(kurt), ROUNDUP(kmin,0), kurt),
// solve for coefficients, retrying across starting values and (if needed)
// slightly bumped kurtosis until a valid monotonic solution is found
coeffs, FSolveBump(skew, kurt),
// general random numbers
IF(
kurtTooSmall,
"ERROR: kurtosis too small for skew = " & skew & "; must be at least " & TEXT(kmin, "0.00"),
IF(
AND(skew = 0, kurt = 0),
// plain standard normal noise -- no Fleishman transform needed
NORM.INV(RANDARRAY(rows, cols), 0, 1),
IF(
INDEX(coeffs, 1, 6) = 0,
"ERROR: no valid distribution found for skew = " & skew & ", kurt = " & kurt,
// use Flieshman method
LET(
z, NORM.INV(RANDARRAY(rows, cols), 0, 1),
b, INDEX(coeffs, 1, 1),
c, INDEX(coeffs, 1, 2),
d, INDEX(coeffs, 1, 3),
-c + b*z + c*z^2 + d*z^3
)
)
)
)
)
);