1

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.

pepi55
  • 57
  • 6

1 Answers1

1

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.

Nils Pipenbrinck
  • 83,631
  • 31
  • 151
  • 221
  • Thanks that solved the repetitive number problem. Though I still get the same numbers every time i run the program :/ or am I missing something EDIT: adding * time to the random seed seems to fix it. It'll do for now, thanks! – pepi55 Feb 02 '14 at 23:21
  • Nope... apparently it repeats the same 3 patterns for some reason when the application is ran 3 times in a row with a minute separation. – pepi55 Feb 02 '14 at 23:32
  • Really sorry for spamming but I've noticed that seeding only time does do the job. How weird... I mean if rand() is multiplied by time how does it still give repetitive numbers? – pepi55 Feb 02 '14 at 23:38