Question

I have seen a lot of posts about the WELLRNG512. Supposedly I have concluded that it would be a better choice than the Mersenne Twister for a roguelike dungeon crawler. I am trying to get this piece of code to generate random numbers and behave much like rand().

Code used:

static unsigned long state[16];
static unsigned int index = 0;

int main (void) {
    int i;

    for (i = 0; i < 16; i++) {
        index = i;
        printf("random: %lu\n", WELLRNG512());
    }

    return 0;
}

unsigned long WELLRNG512 (void) {
    unsigned long a, b, c, d;

    a = state[index];
    c = state[(index+13)&15];
    b = a^c^(a<<16)^(c<<15);
    c = state[(index+9)&15];
    c ^= (c>>11);
    a = state[index] = b^c;
    d = a^((a<<5)&0xDA442D24UL);
    index = (index + 15)&15;
    a = state[index];
    state[index] = a^b^d^(a<<2)^(b<<18)^(c<<28);

    return state[index];
}

Expected results:

random: 231544
random: 542312
random: 588690
(...etc...)

Acquired results:

random: 4195755
random: 4195755
random: 4195755
(...etc...)

Has anyone got any idea how I can successfully make that piece of code behave like rand()?

P.S.: I'm a student, definitely not a mathematician, so please, explain your answer in great detail if you're going to use any kind of hieroglyphs to explain formula's, etc.

Was it helpful?

Solution

There are some things wrong with the code. The most important one: You are never calling the random number generator. This line here:

   printf("random: %lu\n", WELLRNG512);

Prints the address of the WELLRNG512 function. It doesn't call it. To fix this try:

   printf("random: %lu\n", WELLRNG512());

Second: The state array have to be filled with random data. Just for testing I threw something together based on the rand() function. That may or may not be a clever way to seed the state array, but it is good enough to get some random data out of your function.

/* seed the state array */
for (i = 0; i < 16; i++)
  state[i] = rand()^(rand()<<16)^(rand()<<31);

Last thing: The function WELLRNG512 increments the index variable itself. There is no need to do this in the test loop found in main.

My complete main function looks like this:

int main (void) {
    int i;

    /* seed */
    for (i = 0; i < 16; i++)
      state[i] = rand()^(rand()<<16)^(rand()<<31);

    for (i = 0; i < 16; i++) {
        printf("random: %lu\n", WELLRNG512());
    }

    return 0;
}

That should fix your problems.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top