Original Post

I need a function for generating random numbers between 0 and 1. I’ve tried searching the Web for such functions, but every one seems to be targeted for a specific platform or is too difficult to adapt, so does anyone have a working function they would like to share?

13 Replies

There’s one by DogP in libgccvb, but I think (correct me if I’m wrong) it only works on hardware.

I chose an easy solution for BLOX2 and VUE Snake, which is a counter which is increased on every CPU cycle. When the counter reaches a certain value, set it to 0 and count up again. Using the modulo operation, you can then always derive a random number from that value. If you want a random number between 0 and 255 for example:

random = prng_counter % 256;

If you only need a 0 or 1, you can of course always switch around the counter:

if(prng_counter) prng_counter = 0; else prng_counter = 1;

Well, by “between 0 and 1” I mean “larger than 0 but smaller than 1”. I have tried using a counter like you said, but then I could only use it once?

I too am interested in getting random numbers. What is the modulo operation?

It’s an operator that returns the remainder of a division, and it’s represented by the % sign in C and usually by MOD in BASIC. For example, 10 % 3 equals 1.

HorvatM schrieb:
Well, by “between 0 and 1” I mean “larger than 0 but smaller than 1”.

I see. Hmm, you could do it the same way. Since working with floats is slow, you could use fixed point math. For example, use numbers between 0 and 100, where 100 is 1, 95 is 0.95, 3 is 0.03 and so on.

HorvatM schrieb:
I have tried using a counter like you said, but then I could only use it once?

You always let it run in the background, and only derive random numbers from it. So you have an always available, rapidly changing “seed” to get a random number. A very simplified example:

while(1) //main loop
{
   prng_counter++;
   do_something();
   if(user_moves()) random = prng_counter % 100;
}

(“prng” stands for “pseudo random number generator”.)

VirtualChris schrieb:
I too am interested in getting random numbers. What is the modulo operation?

HorvatM just explained it nicely. Just a little addition: you use the modulo operator to get numbers in a certain range. % 100 for example always returns numbers between 0 and 99 (both included), because the remainder can not become greater than the divisor. It’s a very useful function. 🙂

Oh… I think I get it now. Thanks.

I don’t understand. To use these examples, do I need to put
int random=0, prng_counter=0;
at the beginning of my program, or what? I put this code in my code, with the int random=0, prng_counter=0; line in and I just get an opponent that goes left, down, up and right with no random movement whatsoever.

{ 
   e=e+1;
     prng_counter=prng_counter+1;
   random = prng_counter % 256;
   if ((random<64) && (opponentx<160) && (e<60)) opponentx=opponentx+1;
   if ((random>63) && (random<128) && (opponentx>-80) && (e<60))  opponentx=opponentx-1;
   if ((random>127) && (random<196) && (opponenty<11) && (e<60))  opponenty=opponenty+1;
   if ((random>195) && (opponenty>-40) && (e<60))  opponenty=opponenty-1;
   // if (prng_counter>60) prng_counter=0;
   if (e>60) e=0;
  • This reply was modified 12 years, 9 months ago by VirtualChris.

VirtualChris,

This random number method will not work for your application. The only way this random number generation will work is when you rely on user input as well.

Another way to generate “random numbers” is with random number tables. Basically, you make a large array, and fill it with “random” numbers. You could generate the numbers yourself by rolling dice. Here is a quick example…

static int rand_num_table[12] = {57, 2372, 572, 1217, 32131, 121, 21178, 7278, 3027, 182, 10979, 99};
int randomPointer = 0;

int getRandom(int range) {
  randomPointer++;
  if (randomPointer >= 12) randomPointer = 0;
  return rand_num_table[randomPointer]%range;
}

Now whenever you want a random number, you would just call getRandom() with the range (so if you wanted a number between 0 and 9, it would be getRandom(10))

Now this would be pretty boring because each game would be the same. So one method is to pick a new starting point by using the title screen, like with this code…

//display warning graphic
while (vbReadPad()==0) {
  randomPointer++;
}
  randomPointer %= 12;

You can get even more “random” by changing the randomPointer whenever a button is pressed. Basically, have a counter in your main loop, and any time it sees a button is pressed, add the counter to randomPointer, then clear the counter (and of course make sure randomPointer is in range).

You would want more than 12 random numbers in your table too, maybe use excel to generate a lot, or find random tables online. And you may only want to use u8 rather than int being you will probably not need a range greater than 255 and negative numbers are generally not used for random numbers. And of course you would need to change the number 12 in the above examples to the actual size of the array you use (use the sizeof feature if the compiler supports it, I didn’t check)

So what you should have learned by now is random numbers do not exist, but you can get “random enough” by incorporating tables, timers, and user input. All the above is from the top of my head, so use it as more of an explanation rather than actual code.

OK, I understand that there is no such thing as a random number. But using your example, say I want a number from one to four. What would be the name of the variable that’s value I made is from one to four?

	static int rand_num_table[4] = {1, 2, 3, 4}; 
	int randomPointer = 0; 

	int getRandom(int range) { 
	randomPointer++; 
	if (randomPointer >= 4) randomPointer = 0; 
	return rand_num_table[randomPointer]%range; 
	} 

I have made it call a variable number by doing the following:

e=e+1;
if (e>60) e=0, getRandom(3);

By the way, your code did compile, so I’m using it.

you would do something like this…

int main() {
  int randNum;
  //... other code here...

  while(something) {
    e=e+1;
    if (e>60) {
      e = 0;
      randNum = getRandom(5);
    }
    // at this point, use randNum to refer to the
    // random number you just got
  }

I have to use the number 5 to get a value 0 to 4. 5 means 5 unique numbers (which would be 0, 1, 2, 3, 4). This makes more sense when you consider bases (binary is base 2, has 0 and 1. The one we use for everyday math which is decimal or base 10 has 0 to 9, which is 10 different numbers. Hex is base 16, which has 0 to f, which is 16 different numbers.)

I dont know if you are just testing or what, but with your random array of 1,2,3,4 it will not seem random at all (the first time you call the random function you will get 1, the next 2, and so on).

Oh, and the random numbers in the array should extend the whole range allowed for the type of variable you are using (so u8 would range from 0 to 255, unsigned int would range from 0 to 65535). The % operator will make sure it is within the range you want. The advantage of doing it this way is you can reuse the random array next time when you want a value between 0 and 9 without having to make a new array.

Ok, so that code won’t produce a “random” number between 0-4? What code can I use to get one once e reaches 60?

You fill rand_num_table with a lot of random numbers. That’s how you get a random number out of my code. Then the only other trick is to try to keep changing the index value, which you would have to do with human input and timing stuff.

You gotta really take the time to learn c better so that all this stuff makes sense. Copying code you don’t understand is bad practice, and can lead to many problems. Then after you go through a lot of lessons and learn C (yes, this will take time), you can copy source code, but if you dont understand why something does what it does, ask on here so that you understand it. That way you can adapt the sample code based on your needs, and it further helps you learn the language. The best way I would reccommend learning C is with a good book, but you could probably find something fine online.

Keep in mind, a lot of us have had college level courses in programming which most likely included everything from assembly, basic, c, and c++ or java. And the difference between lower level languages (assembly and basic) and higher level languages (c, c++, java) is huge. Once you learn to use a higher level language, you can much more quickly create useful stuff.

I’d like to revisit this topic, since random numbers are mighty useful in games. So I did a search for random number generators and found this page:

http://www.math.sci.hiroshima-u.ac.jp/~m-mat/MT/MT2002/emt19937ar.html

Specifically, this .c file:

http://www.math.sci.hiroshima-u.ac.jp/~m-mat/MT/MT2002/CODES/mt19937ar.c

This is a random number generator based on the Mersenne Twister, which is supposedly reliable and fast. It requires you to either give it a seed to start with, or set up an array with some seed numbers. From there on it will give you nice random numbers.

Now, the C file linked above will error out horribly if you try to include it in a VB project. Thing is, the genrand_real functions contain stuff that will not compile on VB. The thing also has an stdio.h include and a main() that we’ll want to remove.

Luckily, this file has a very liberal license, so it can be modified to our wishes. Attached is a modified mt19937ar.c that properly gives you pseudo-random numbers on VB! (I tried it on one of the demo files, and it seems to be returning random numbers quite nicely!)

Usage:

//On init:
init_genrand(18293); //Or any number you like

//Whenever you need it:
int randomnumber = genrand_int32()%10; //%10 means between 0 and 9
Attachments:

 

Write a reply

You must be logged in to reply to this topic.