Jump to content
  • Advertisement
Sign in to follow this  
peter_b

Bad psuedo random function :/

This topic is 4591 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

Hello. Iv been trying to write a psuedo random function. But i get bad random numbers! If i call the function with min as 0 and max as 4. It will only return 1 or 3. Nothing else, ever. :/ It should return 0,2 and 4 sometimes too. I dont know what im doing wrong.
int psuedo_random_t::get_random_int(int min, int max)
	{
		if( min >= max ) // bad input
			return min;

		// update seed
		m_seed = (m_gen1 * m_seed) + m_gen2;

		// Use modulo operator to ensure < max
		int val = m_seed % (max - min);
		if(val < 1)
			val = val * -1; // Keep it positive

		return val + min; 
	}

gen1&2 is initialized like this: m_gen2 = 3917; m_gen1 = (m_gen2 / 2); and m_seed is time. Anyone know why this is? :/ Thanks in advance!

Share this post


Link to post
Share on other sites
Advertisement
(1) C and C++ both provide a function rand() that generates a pseudo-random number. It isn't great, but its good enough for simple thins.

(2) boost provides a number of PRNG implementations that are considerably better than the standard one.

(3) Numerical Recipes has a chapter on pseudo-random number generation. If you're interested in the theory, its a good start.

CM

Share this post


Link to post
Share on other sites
Do not try to develop your own PRNG - you *will* make a bad one and your users will curse you (see C&C Generals).
This is nothing personal, it's just that PRNGs are a black art. Use e.g. Mersenne Twister instead.

Problems with the current approach:
- it's an LCG (Linear Congruential Generator), where it is absolutely critical that you make mathematically sound choices of parameters. (A=3917, B=1958, M=2**32) are extremely poor because you aren't taking the whole result modulo a prime M, A is too small, and B isn't relatively prime WRT M.
- You take the result modulo (max-min). After adding min to that, you will only get values in [min, max).
- Using modulo to trim the result down to an interval is really bad, especially if interval size = 2**n. That means you only examine the lowest bits, which aren't distributed as nicely as the upper ones. Instead, scale your RNG down to [0.f, 1.f) and multiply by interval size.

HTH+HAND

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

Participate in the game development conversation and more when you create an account on GameDev.net!

Sign me up!