-
Notifications
You must be signed in to change notification settings - Fork 0
/
mt19937.cpp
executable file
·53 lines (41 loc) · 1.36 KB
/
mt19937.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
//Mersenne-Twister 19937 pseudorandom number generator.
//Reference implementation at:
//http://www.math.sci.hiroshima-u.ac.jp/~m-mat/MT/MT2002/CODES/mt19937ar.c
#include "mt19937.h"
void mt19937_init(mt19937_ctxt_t *ctxt, unsigned int seed)
{
ctxt->state[0] = seed;
for(ctxt->idx = 1; ctxt->idx < MT_N; ctxt->idx++)
ctxt->state[ctxt->idx] = (1812433253 * (ctxt->state[ctxt->idx - 1] ^ (ctxt->state[ctxt->idx - 1] >> 30)) + ctxt->idx);
ctxt->idx = MT_M + 1;
}
unsigned int mt19937_update(mt19937_ctxt_t *ctxt)
{
unsigned int y, k;
static unsigned int mag01[2] = {0, MT_MATRIX_A};
if(ctxt->idx >= MT_N)
{
for(k = 0; k < MT_N - MT_M; k++)
{
y = (ctxt->state[k] & MT_UPPER_MASK) |
(ctxt->state[k + 1] & MT_LOWER_MASK);
ctxt->state[k] = ctxt->state[k + MT_M] ^ (y >> 1) ^ mag01[y & 1];
}
for(; k < MT_N - 1; k++)
{
y = (ctxt->state[k] & MT_UPPER_MASK) |
(ctxt->state[k + 1] & MT_LOWER_MASK);
ctxt->state[k] = ctxt->state[k + (MT_M - MT_N)] ^ (y >> 1) ^ mag01[y & 1];
}
y = (ctxt->state[MT_N - 1] & MT_UPPER_MASK) |
(ctxt->state[0] & MT_LOWER_MASK);
ctxt->state[MT_N - 1] = ctxt->state[MT_M - 1] ^ (y >> 1) ^ mag01[y & 1];
ctxt->idx = 0;
}
y = ctxt->state[ctxt->idx++];
y ^= (y >> 11);
y ^= (y << 7) & 0x9d2c5680UL;
y ^= (y << 15) & 0xefc60000UL;
y ^= (y >> 18);
return y;
}