Here is one I use in a big project:
Code:
/*
Random number generator
Hull–Dobell Theorem :
Linear congruential generator x <-- (x * a + c) % m is correct for:
m and c are relatively prime,
a − 1 is divisible by all prime factors of m,
a − 1 is divisible by 4 if m is divisible by 4.
*/
MaxDouble = 1.7976931348623158 * 10^308;
MinDouble = -1.7976931348623158 * 10^308;
Rndm_m = 256 * 256 * 256 * 256 ; // Modulo: 2^32
Rndm_m1 = Rndm_m - 1;
Rndm_a = 4 * 8191 + 1; // 8191 is a prime
Rndm_c = 8167; // a prime, less than 8191
Rndm_n = 59933; // the seed : ANY value will do
// next seed is then "Rndm_n = (Rndm_n * Rndm_a + Rndm_c) % Rndm_m;"
// provide a random integer in [0 .. k-1]
function irand(k)
(
Rndm_n = (Rndm_n * Rndm_a + Rndm_c) % Rndm_m;
floor(k * Rndm_n / Rndm_m);
);
// provide a random float in [0 .. 1]
function frand()
(
(Rndm_n = (Rndm_n * Rndm_a + Rndm_c) % Rndm_m) / Rndm_m1;
);
// provide a random float in [a b]
function frand(a, b)
(
a + (b - a) * (Rndm_n = (Rndm_n * Rndm_a + Rndm_c) % Rndm_m) / Rndm_m1;
);
// provide a random float between a and b according to an exponential distribution
function xrand(a,b)
(
(a <= 0) ? a = MinDouble : a = log(a);
(b <= 0) ? b = MinDouble : b = log(b);
exp (a + (b - a) * (Rndm_n = (Rndm_n * Rndm_a + Rndm_c) % Rndm_m) / Rndm_m1);
);
The idea is that, whatever you use in your algorithm (irand, frand, xrand), you can run it again identically by just resetting the seed, the variable Rndm_n.
Hope that help.
J. Jack.
PS: just for the info, the algorithm referenced by
https://forum.cockos.com/showpost.ph...45&postcount=2 was first devised for the implementation of the APL\360 language by Kenneth E. Iverson in the sixties, with these precise values 16807 (aka 7^5) and 2147483647 (2^31 - 1).