Class ZigguratSampler
- java.lang.Object
-
- org.apache.commons.rng.sampling.distribution.ZigguratSampler
-
- All Implemented Interfaces:
ContinuousSampler
,SharedStateContinuousSampler
,SharedStateSampler<SharedStateContinuousSampler>
- Direct Known Subclasses:
ZigguratSampler.Exponential
,ZigguratSampler.NormalizedGaussian
public abstract class ZigguratSampler extends java.lang.Object implements SharedStateContinuousSampler
Modified ziggurat method for sampling from Gaussian and exponential distributions.Uses the algorithm from:
McFarland, C.D. (2016)
"A modified ziggurat algorithm for generating exponentially and normally distributed pseudorandom numbers".
Journal of Statistical Computation and Simulation 86, 1281-1294.Note: The algorithm is a modification of the
Marsaglia and Tsang "Ziggurat" method
. The modification improves performance by:- Creating layers of the ziggurat entirely inside the probability density function (area B); this allows the majority of samples to be obtained without checking if the value is in the region of the ziggurat layer that requires a rejection test.
- For samples not within the main ziggurat (area A) alias sampling is used to choose a layer and rejection of points above the PDF is accelerated using precomputation of triangle regions entirely below or above the curve.
\ ----------+\ | \ B |A \ -------------+\ | \
Sampling uses
UniformRandomProvider.nextLong()
.- Since:
- 1.4
- See Also:
- McFarland (2016) JSCS 86, 1281-1294
-
-
Nested Class Summary
Nested Classes Modifier and Type Class Description static class
ZigguratSampler.Exponential
Modified ziggurat method for sampling from an exponential distribution.static class
ZigguratSampler.NormalizedGaussian
Modified ziggurat method for sampling from a Gaussian distribution with mean 0 and standard deviation 1.
-
Field Summary
Fields Modifier and Type Field Description private static int
MASK_INT8
Mask to extract the lowest 8-bits from an integer.private static long
MAX_INT64
Mask to create an unsigned long from a signed long.private UniformRandomProvider
rng
Underlying source of randomness.private static double
TWO_POW_63
2^63.
-
Constructor Summary
Constructors Constructor Description ZigguratSampler(UniformRandomProvider rng)
-
Method Summary
All Methods Static Methods Instance Methods Concrete Methods Modifier and Type Method Description (package private) static double
interpolate(double[] v, int j, long u)
Compute the value of a point using linear interpolation of a data table of values using the provided uniform deviate.(package private) long
nextLong()
Generates along
.(package private) long
randomInt63()
Generates a positivelong
in[0, 2^63)
.(package private) java.lang.String
toString(java.lang.String type)
Generate a string to represent the sampler.-
Methods inherited from class java.lang.Object
clone, equals, finalize, getClass, hashCode, notify, notifyAll, toString, wait, wait, wait
-
Methods inherited from interface org.apache.commons.rng.sampling.distribution.ContinuousSampler
sample, samples, samples
-
Methods inherited from interface org.apache.commons.rng.sampling.SharedStateSampler
withUniformRandomProvider
-
-
-
-
Field Detail
-
MASK_INT8
private static final int MASK_INT8
Mask to extract the lowest 8-bits from an integer.- See Also:
- Constant Field Values
-
MAX_INT64
private static final long MAX_INT64
Mask to create an unsigned long from a signed long. This is the maximum value of a 64-bit long.- See Also:
- Constant Field Values
-
TWO_POW_63
private static final double TWO_POW_63
2^63.- See Also:
- Constant Field Values
-
rng
private final UniformRandomProvider rng
Underlying source of randomness.
-
-
Constructor Detail
-
ZigguratSampler
ZigguratSampler(UniformRandomProvider rng)
- Parameters:
rng
- Generator of uniformly distributed random numbers.
-
-
Method Detail
-
toString
java.lang.String toString(java.lang.String type)
Generate a string to represent the sampler.- Parameters:
type
- Sampler type (e.g. "exponential").- Returns:
- the string
-
nextLong
long nextLong()
Generates along
.- Returns:
- the long
-
randomInt63
long randomInt63()
Generates a positivelong
in[0, 2^63)
.In the c reference implementation RANDOM_INT63() obtains the current random value and then advances the RNG. This implementation obtains a new value from the RNG. Thus the java implementation must ensure a previous call to the RNG is cached if RANDOM_INT63() is called without first advancing the RNG.
- Returns:
- the long
-
interpolate
static double interpolate(double[] v, int j, long u)
Compute the value of a point using linear interpolation of a data table of values using the provided uniform deviate.value = v[j] + u * (v[j-1] - v[j])
This can be used to generate the (x,y) coordinates of a point in a rectangle with the upper-left corner at
j
and lower-right corner atj-1
:X[j],Y[j] |\ | | \| | \ | |\ Ziggurat overhang j (with hypotenuse not pdf(x)) | | \ | u2 \ | \ |-->u1 \ +-------- X[j-1],Y[j-1] x = X[j] + u1 * (X[j-1] - X[j]) y = Y[j] + u2 * (Y[j-1] - Y[j])
- Parameters:
v
- Ziggurat data table. Values assumed to be scaled by 2^-63.j
- Index j. Value assumed to be above zero.u
- Uniform deviate. Value assumed to be in[0, 2^63)
.- Returns:
- value
-
-