lua-users home
lua-l archive

[Date Prev][Date Next][Thread Prev][Thread Next] [Date Index] [Thread Index]


On 17/03/2010, at 7:24 AM, Christopher Eykamp wrote:

> 
> On 3/16/2010 11:18 AM, Geoff Leyland wrote:
>> 
>> On windows I got the same results as Christopher.
>> 
>> Lua just uses the system's rand, and what you're learning is that rand isn't a great random number generator, and that Windows' implementation is not the best.  lhf's lrandom is surely better: http://www.tecgraf.puc-rio.br/~lhf/ftp/lua/
>>   
> Even a poorly designed random number generator should generate different streams from different seeds.  Is it possible that lua is not passing the seed off to the system's random function properly in some implementations?

Sorry, you might be right.  There could be an interaction between the assembler Lua uses to convert a double to an integer on Windows and srand.  I'm way out of my depth here, but I get this output:


Normal
3590324224      8258=2521       15694=4790      5645=1723       409=125
2751463424      723=221 2443=746        138=43  21381=6526
274726912       10206=3115      16556=5053      19409=5924      13667=4171
2109734912      24100=7355      14574=4448      960=293 5546=1693
4072669184      26493=8086      2768=845        25807=7876      3290=1005
872415232       10884=3322      21218=6476      2888=882        1798=549
ASM
3590324224      38=12   7719=2356       21238=6482      2437=744
2751463424      38=12   7719=2356       21238=6482      2437=744
274726912       38=12   7719=2356       21238=6482      2437=744
2109734912      38=12   7719=2356       21238=6482      2437=744
4072669184      38=12   7719=2356       21238=6482      2437=744
872415232       38=12   7719=2356       21238=6482      2437=744


from this program:


#include <stdlib.h>
#include <stdio.h>
#include <math.h>
#include <stddef.h>

void srand_normal(double seed)
{
  ptrdiff_t s = (ptrdiff_t)seed;
  srand((unsigned)s);
  printf("%u\t", seed);
}

void srand_asm(double seed)
{
  ptrdiff_t s;
  __asm fld seed   __asm fistp s;
  srand((unsigned)s);
  printf("%u\t", seed);
}

void test()
{
  unsigned i;
  for (i = 0; i < 4; ++i)
  {
    unsigned r = rand();
    printf("%u=%.0f\t", r, floor((r%RAND_MAX) / (double)RAND_MAX * 10000.0 + 1.0));
  }
  printf("\n");
}

int main(void)
{
  double seeds[] = {3063121584.0,2428144928.0,3559301251.0,4287790062.0,2737803158.0,2458923424.0};
  unsigned i;
  printf("RAND_MAX=%u\n", RAND_MAX);
  printf("Normal\n");
  for (i = 0; i < sizeof(seeds) / sizeof(double); ++i)
  {
    srand_normal(seeds[i]);
    test();
  }
  printf("ASM\n");
  for (i = 0; i < sizeof(seeds) / sizeof(double); ++i)
  {
    srand_asm(seeds[i]);
    test();
  }
  return 0;
}