Pseudo-random numbers

Okay, so I’m trying to figure out a way to reliably generate a list of numbers in Flash that seem random, but come out the same way every time when fed the same seed.

Now, I’ve seen some ideas for how to do this on the internet, but they’re usually not very robust. Here is one example. I think it was originally written in Java or Director or something. If you recognize where it came from, please post about it. Whatever language and tutorial I got it from, since it’s only math, it was pretty easy to port to Flash:


//NOT a good pseudo-random number generator.  Only decent decimal places for inputs between 0 and 100 or so, so that's how we're using it.
function pseudoRandom(maxValue:Number) {
 if (_root.PRNGSeed>100) {
  _root.PRNGSeed = 0;
 } else {
  _root.PRNGSeed++;
 }
 x = _root.PRNGSeed;
 x = (x << 13) ^ x;
 foo = (1.000-((x*(x*x*15731+789221)+1376312589) & 0x7FFFFFFF)/(1073741824.0));
 if (foo<0) {
  foo *= -1;
 }
 foo *= maxValue;
 return foo;
}

I was unsatisfied with this solution because the higher the seed number gets, the more “polarized” the results seem to be. It returns a number between 1 and 0, and by multiplying this by, say, 256, you will always get a number between 0 and 255, yes… but when the seed value gets above 100, weird things start becoming obvious. Beyond 300 or so, the result is always one of 5 values. But the time the seed is over 1000 or so, using this method, the answer is always 0 or 255.

I don’t know what this phenomenon is called, I just observe it happening when this number generator is fed high integers as a seed. And I don’t know enough about math to figure out what is causing it and why and how to fix it. In my example, I’ve forced the seed to loop after 100, so the polarization hopefully won’t become too obvious to the player… but this limits the complexity of maps (landscapes, enemy attack patterns, clouds… whatever game content you wanted to generate with this pseudo-random number) to 100 possible values, after which the stuff going on will noticibly loop.

Anyway, today I was messing around with Flash 8’s built-in perlinNoise function, and once I got it going, I was delighted to discover that I couldn’t really see any predictable pattern, and no matter how high of a seed number I fed it, it didn’t break down into all black or all white, so I figured whatever internal fractal technique Flash 8 uses, it must be more robust than the code I ripped from that tutorial. I started thinking about ways to use it to generate numbers. Here’s what I came up with:

 import flash.display.BitmapData;
var pRandCounter:Number = 0;
var seed:Number = 0;
var pRandBitData:BitmapData = new BitmapData(2, 2, false, 0x00CCCCCC);
function pRand(seed:Number) {
 pRandBitData.perlinNoise(2, 2, 6, _root.seed, false, true, 1, true, null);
 return Math.abs (Math.cos(pRandBitData.getPixel(1, 1)));
}
_root.onEnterFrame = function() {
 _root.seed++;
 _root.pRandCounter = Math.ceil(pRand(_root.seed)*100);
};

I was pretty sure that the Math.cos was a clever bit would guaruntee that whatever kind of crazy number the pRandBitData returned (which, unfortunately, is a string which varies greatly in the number of digits it returns, so I can’t just divide it by some theoretical max value to get a result between 1 and 0.) it would get turned into an angle between 0 and 360. I figured if the number was freakin’ huge, it would be over 360, and so it would wrap around to 0 and keep going. Does anyone know if Math.cos really works that way or not?

Unfortunately, in practice, this technique, while it doesn’t break down no matter how high the seed gets, and while it does seem to return values from all over the range, it seems to return a value of 100 surprisingly often. I really have no idea what to make of this. (As you math guys may have noticed… I’m not a math guy. :wink: )

Can anyone propose a better way of generating a seemingly endless list of random-looking numbers between 0 and 1, when it’s fed incrementing integers as a seed?

I wish I could port [color=#0000ff]Mersenne twister[/color] into Flash, but it’s pretty complicated code, at least by my standards. I don’t know enough C to make the C into AS.

Does anyone know of a better way to do pseudo-random numbers in Flash?

Thanks in advance for any helpful replies.