Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations strongm on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

Borland random() function 1

Status
Not open for further replies.

KarlSciberras

Programmer
Dec 8, 2006
9
MT
The following is a small program which
generates random numbers which can be
either 1 or -1:

Code:
#include <stdlib.h>
#include <stdio.h>
#include <time.h>

int main(void)
{
   int i;

   randomize();
   printf("Ten random numbers of either -1 or 1\n\n");
   for(i=0; i<10; i++)
       printf("%d\n", random(100)>30 ? -1 : 1);
   system("pause"); 
   return 0;
}

The output is shown below (in red) :


Ten random numbers of either -1 or 1

-1
1
1
1
-1
1
-1
-1
-1
1
Press any key to continue . . .


The program above is not mine, but it works fine.
I have been asked to analyze this code and this
is where I need some particular help.
I cannot understand the following
part of the code:

Code:
random(100)>30 ? -1 : 1

I cannot understand why (100) is passed to the
random function when only two possible outcomes
are expected. I also cannot understand the use of
>30. What I noticed however is that when >30
is removed, the outcome is less random and more
repetitive. But how was this value determined ?
 
Code:
random(100)>30 ? -1 : 1
is roughly equivalent to:
Code:
if (random(100) > 30)
{
    return -1;
}
else
{
    return 1;
}

The 100 in the random() function is called the "seed." This is the number the function uses to generate the "random" number. You can use any number here.

The random number generator is not truly random. The problem here is if you use the same seed, you will get repetitive results as you noticed.

For the number to truly be random, the seed also has to be random. So how do you generate a random number for the seed of a random number generator? There is a whole division of computer science devoted to this theory so don't try to answer that unless you are working on your Ph.D. :)

One simple solution is to use a time for the seed. Somewhere I have a "seed" generator that uses the date and time to generate the seed. It isn't too hard to figure out.

If you are not too interested in creating a "true" random number, you can use the 100 (or any number you want) as shown.

James P. Cottingham
-----------------------------------------
[sup]I'm number 1,229!
I'm number 1,229![/sup]
 
That's close 2ffat, but actually, randomize() seeds the random number generator for you in a pseudo-random way. random(N) returns a random number from 0 to N-1, so random(100) returns a random number that is < 100 and >= 0.
 
so you have -1 roughly 30 times of 100, and 1 rest 70 times.
(I said "roughly". So you can have 305 and 695 from 1000 or the like).
So this distribution is not very random ;))
 
itsgd,
[tab]You're right, I was thinking of rand.


James P. Cottingham
-----------------------------------------
[sup]I'm number 1,229!
I'm number 1,229![/sup]
 
tsh73,

I think you meant that -1 has approximately 70%
probability while 1 has approximately 30% probability.
2ffat has shown a piece of code which I think demostrates
this.

Regarding the parameter passed to random:
As itsgsd pointed out, it defines the range.
e.g. random(5) will give you a random number
between 0 and 4. The seed is automatically set
to the current time by the randomize() function.
 
I think you meant that -1 has approximately 70%
probability while 1 has approximately 30% probability.
The word approximately is the key here. Just for the fun of it, I changed the program above to the following and ran it 20 times.
Code:
#include <stdlib.h>
#include <stdio.h>
#include <time.h>

int main(void)
{
   int PCount = 0, NCount = 0;

   randomize();
   printf("Ten random numbers of either -1 or 1\n\n");
   for(int i=0; i<100; i++)
   {
        if (random(100) > 30) ++NCount;
        else ++PCount;
        {

        }
   }
   printf("The count of Negative numbers is %d\n", PCount);
   printf("The count of Positive numbers is %d\n", NCount);
   system("pause");
   return 0;
}

The results were interesting. The ratio of "negative" to "positive" were 67/33, 65/35, 73/27, 72/28, 58/42, 63/37, 62/38, 67/33, 72/28, 76/24, 70/30, 74/26, 61/39, 66/34, 76/24, 70/30, 71/29, 66/34, 69/31, & 66/34.

Then I changed "random(100) > 30" to "random(100) > 50" and ran it 10 times. The ratio changed to 52/48, 50/50, 55/45, 47/53, 55/45, 47/53, 41/59, 45/55, 47/53, & 44/56. Notice that I got move positive numbers than negative numbers.

It would be interesting to know what others get.



James P. Cottingham
-----------------------------------------
[sup]I'm number 1,229!
I'm number 1,229![/sup]
 
I also did the following which differs from the above program in that it runs 10 times with the same random seed whereas the above program uses a new seed for each iteration.

Code:
#include <stdlib.h>
#include <stdio.h>
#include <time.h>

int main(void)
{
   int PCount, NCount;

   randomize();
   printf("Ten ratios of random numbers of either -1 or 1\n\n");
   for (int j = 0; j < 10; ++j)
   {
       PCount = 0;
       NCount = 0;
       for(int i=0; i<100; i++)
       {
           if (random(100) > 30) ++PCount;
           else ++NCount;
       }
       printf("The count of negative to postive numbers is %d to %d\n", NCount, PCount);
   }
   system("pause");
   return 0;
}




James P. Cottingham
-----------------------------------------
[sup]I'm number 1,229!
I'm number 1,229![/sup]
 
2ffat,

Our results are very similar.
When using random(100) > 50 the chances
of each outcome are equally spread between
"positive" and "negative" numbers. Meaning that
sometimes the positive outcome slightly surpasses
the negative outcome and vice verca.

Please note the following fault in your code :
Code:
printf("The count of Negative numbers is %d\n", PCount);
printf("The count of Positive numbers is %d\n", NCount);
(swap PCount with NCount)

regarding the following:
I also did the following which differs from the above program in that it runs 10 times with the same random seed whereas the above program uses a new seed for each iteration.

None of your programs make a new seed for each
iteration. The seed is generated by randomize()
which is not within any loop. Since randomize()
is not within a loop the random number generator
is initialized only once by a new seed value,
which is returned by the system timer.

However i think that the seed must only be set
once at the start of the program.
correct me if i'm wrong.
 
KarlSciberras,

[tab]I thought I had put the randomize function in the loop in the second program. Sorry, my mistake. Also, sorry about the mixup in the variables. I wrote this on the fly and didn't check it out very carefully as you can tell.

[tab]AFAIK, you are correct, there is no need to reseed the generator within the program. I thought it would be interesting to see if there was much of a difference between the two.

[tab]Just a thought, without seeing what the original program was used for, it almost seems to be that random(100) > 30 would be used for a gaming program where the "house" wins more often then it loses. :)



James P. Cottingham
-----------------------------------------
[sup]I'm number 1,229!
I'm number 1,229![/sup]
 
James,

Yes, that would have been a good case.
It's acually part of an algorithm used
to draw a random graphic. The random
function in this case determines on
which axis a certain part of the graphic
will be drawn. In fact a problem is that
the chances of each outcome are not
equally spread, resulting in a less
symmetrical image.

Thanks everyone !!!!
 
Correct me if I'm wrong, but random(N) returns 0 to (N-1), so a test of random(100) > 50 is a bit off. It looks as though it ought to be 50%, but it isn't.

It's simpler to think of random(10) > 5.

Possibilities are:

0, 1, 2, 3, 4, 5 (all 5 or less; 6 possibilities)
6, 7, 8, 9 (4 possibilities greater than 5).

2ffat, you're absolutely right, there is no need to re-randomise in the middle of your code. The point of the random number generator is it not only produces a number that bears no obvious relationship to the previous one, but it also leaves the seed in a state that means the next number will bear no obvious relationship to the current one, either.

Since the code is designed to make a graphic, it's quite nice to allow the user to input the seed (or to tell them what the seed is, if you use randomise). That way they can recreate a particularly attractive graphic by noting down its seed.
 
Since the code is designed to make a graphic, it's quite nice to allow the user to input the seed (or to tell them what the seed is, if you use randomise). That way they can recreate a particularly attractive graphic by noting down its seed.
Neat idea.


James P. Cottingham
-----------------------------------------
[sup]I'm number 1,229!
I'm number 1,229![/sup]
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top