Misplacement of srand

F

Felipe Ribeiro

Hi everybody!

I wrote a small program to simulate a game of craps. Here's the code:
============================================================
#include <stdio.h>
#include <stdlib.h>
#include <time.h>

#define true 1
#define false 0

typedef int bool;

int roll_dice(void);
bool play_game(void);

int main(void)
{
char play_again;
int wins = 0, losses = 0;

do {
if (play_game()) {
printf("You win!\n\n");
wins++;
} else {
printf("You lose!\n\n");
losses++;
}

printf("Play again? ");
play_again = getchar();
getchar();
printf("\n");
} while (play_again == 'y' || play_again == 'Y');

printf("Wins: %d Losses: %d\n\n", wins, losses);

return 0;
}

bool play_game(void)
{
int first_roll, point;

srand((unsigned) time(NULL));

first_roll = roll_dice();
printf("You rolled: %d\n", first_roll);
switch (first_roll) {
case 7:
case 11:
return true;
case 2:
case 3:
case 12:
return false;
}

printf("Your point is %d\n", first_roll);
for (;;) {
point = roll_dice();
printf("You rolled: %d\n", point);
if (point == first_roll)
return true;
if (point == 7)
return false;
}
}

int roll_dice(void)
{
int dice1, dice2;

dice1 = (rand() % 6) + 1;
dice2 = (rand() % 6) + 1;

return dice1 + dice2;
}
============================================================

Initially a had placed srand inside roll_dice, but the result was not
what I wanted. The output would be something like this:
================
You rolled: 5
Your point is 5
You rolled: 5
You win!

Play again? y

You rolled: 2
You lose!

Play again? y

You rolled: 6
Your point is 6
You rolled: 6
You win!

Play again? y

You rolled: 3
You lose!

Play again? y

You rolled: 6
Your point is 6
You rolled: 6
You win!

Play again? n

Wins: 3 Losses: 2
================

As you can see, when calling roll_dice again, the function always
returns the same number. When placing srand inside play_game, as the
code shows, everything goes well. Here's a sample of a correct session
running the program:
===============
You rolled: 6
Your point is 6
You rolled: 9
You rolled: 5
You rolled: 4
You rolled: 4
You rolled: 9
You rolled: 12
You rolled: 5
You rolled: 11
You rolled: 4
You rolled: 11
You rolled: 7
You lose!

Play again? y

You rolled: 5
Your point is 5
You rolled: 4
You rolled: 9
You rolled: 5
You win!

Play again? y

You rolled: 11
You win!

Play again? y

You rolled: 11
You win!

Play again? n

Wins: 3 Losses: 1
===============

I can't understand why I have to put srand inside play_game and not
inside roll_dice. I guess it would make more sense to place it in the
latter since just roll_dice uses it.

I'd really appreciate if somebody could give me a hand.
Thanks in advance.

Felipe
 
B

Ben Bacarisse

Felipe Ribeiro said:
I wrote a small program to simulate a game of craps. Here's the code:
Initially a had placed srand inside roll_dice, but the result was not
what I wanted.
I can't understand why I have to put srand inside play_game and not
inside roll_dice. I guess it would make more sense to place it in the
latter since just roll_dice uses it.

There is some help in the C FAQ: http://c-faq.com/lib/srand.html --
particularly the last paragraph -- but it does not really say "why".

rand() simulates randomness by performing a computation that seems (to
us) chaotic. Repeatedly re-seeding this computation just before
calling rand() messes up the fine work that was done trying to make
the returned results from rand() look random.
 
B

Beej Jorgensen

Felipe Ribeiro said:
I can't understand why I have to put srand inside play_game and not
inside roll_dice. I guess it would make more sense to place it in the
latter since just roll_dice uses it.

Another way of thinking of it is that when you seed the random number
generator, you're giving it a starting point, and it will generate
pseudo-random numbers from there. If you give it the same starting
point again, it will restart and generate the same sequence of numbers
again.

So what you want to do is give it a starting point once (call srand()
with some seed, say the current time), and then call rand() repeatedly
to pull random numbers from the sequence. If you reseed it with the
same number (the current time, depending on how it's measured, might be
the same number if you check it immediately), it will start the sequence
again.

In short: call srand() once at the start of your program, and then call
rand() as many times as you want later on.

-Beej
 
F

Franken Sense

In Dread Ink, the Grave Hand of Beej Jorgensen Did Inscribe:
Another way of thinking of it is that when you seed the random number
generator, you're giving it a starting point, and it will generate
pseudo-random numbers from there. If you give it the same starting
point again, it will restart and generate the same sequence of numbers
again.

So what you want to do is give it a starting point once (call srand()
with some seed, say the current time), and then call rand() repeatedly
to pull random numbers from the sequence. If you reseed it with the
same number (the current time, depending on how it's measured, might be
the same number if you check it immediately), it will start the sequence
again.

In short: call srand() once at the start of your program, and then call
rand() as many times as you want later on.

-Beej

I've written a lot of programs on them in C and lost them. I could
probably inform a google search.
--
Frank

When you encounter seemingly good advice that contradicts other seemingly
good advice, ignore them both.
~~ Al Franken,
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,769
Messages
2,569,581
Members
45,057
Latest member
KetoBeezACVGummies

Latest Threads

Top