-
comparing dice
Hello, i am new to the forum, and programming in general.
I picked up "C for dummies 2nd edition" as an ebook, and have been working my way through it, using code::blocks.
Almost done with my initial read through, then i will go back and reread in-depth. So far, i have managed to make a entire yahtzee game, minus the scoring. Could some one show an example of a decent way to compare dice (which are stored as a array)?
I will post my code that i have done so far:
Code:
/* *****************************
---------- FILE\ ----------
changed: 1/17/2013 @ 11:01pm
main.c , yaht-c
---------- /FILE ----------
-----------------------------
---------- STATUS\ ----------
Looks like i have to add in
scoring, and clean up
code / comments.
yaht-c can now detect if you
roll a yahtzee!
---------- /STATUS ----------
-----------------------------
---------- TO DO\ ----------
1.) get scoring working.
2.) will need a score card.
---------- /TO DO ----------
-----------------------------
---------- IDEAS\ ----------
1.) dice logo [ Improved ;) ]
2.) "non standard" yahtzee
scoring rules? or regular?
---------- /IDEAS ----------
***************************** */
// preprocessor commands
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
// function prototypes
void title();//display game title
void whatdice(int the_dice);//rolls selected dice
int roll();//roll number 1-3 of the current turn
void score();//scoring and / or scratching off
void turn();//keeps calling roll() up to 3 times
int keep_or_not();//prompts user for which dice to keep, or quit game
int rnd(int range);//random numbers for the dice are made here
// global variables
int roll_n=0;//roll number, 1-3 for the current turn
int dice_n=0;//keeps track of what dice we are talking about
int turn_n=0;//turn number
int dice[5];//array which holds the game dice
// *****************************
int main()
{
srand((unsigned)time(NULL));//seed random number generator with clock data
short turns;//was int, changed to short, still compiles
title();// show the title
for(turns = 1;turns<=13;turns++)//13 turns in a standard single player yahtzee game
{
turn();//take another turn
}
return 0;//all done
}
void turn()
{
int score_yet=0;//0 == take another roll, 1 == go score
score_yet = roll();//first roll
if (score_yet == 1)
{
return;//user held all dice, scored. turn is over, so start the next turn
}
else
{
score_yet = roll();//second roll
}
if (score_yet == 1)
{
return;//user held all dice, scored. turn is over, so start the next turn
}
else
{
score_yet = roll();//third roll. no matter what, the turn is over
}
}
int rnd(int range)
{
return(rand()%range);//randomness is so random... or is it?
}
void whatdice(int the_dice)
{
switch (the_dice)//what dice are we talking about here?
{
case 1:
dice[0] = rnd(6)+1;
break;
case 2:
dice[1] = rnd(6)+1;
break;
case 3:
dice[2] = rnd(6)+1;
break;
case 4:
dice[3] = rnd(6)+1;
break;
case 5:
dice[4] = rnd(6)+1;
break;
default://this is always done on the first roll of a turn
dice[0] = rnd(6)+1;
dice[1] = rnd(6)+1;
dice[2] = rnd(6)+1;
dice[3] = rnd(6)+1;
dice[4] = rnd(6)+1;
break;
}
}
int roll()
{
int early=0;//this keeps track of whether we need to score before the third roll of a turn
if (roll_n==0)
{
++turn_n;//this must mean we are on a new turn
}
fflush(stdin);//clear input
roll_n++;//increase the roll count
//i like the idea of the score card being where the player can see it at the start of every turn
printf("\"yaht-c\", yahtzee game in C\nby Rami Davis.\n");
printf("SCORE CARD:1's = | 2's = | 3's = | 4's = | 5's = | 6's = | top bonus = \n 3 of a kind = | 4 of a kind = | full house = | \n [I know, not finished...]\n");
//...will need to be redone so that it is updated as the game goes along
printf("turn #: %i\n", turn_n);//what turn is it?
printf("roll #: %i\n",roll_n);//and what roll is it of that turn?
printf("You rolled: ");
if (roll_n==1)
{
whatdice(0);//on the first roll of every turn, all dice are to be rolled
}
printf("[%i] [%i] [%i] [%i] [%i]\n",dice[0],dice[1],dice[2],dice[3],dice[4]);//display the roll
if(roll_n==1 || roll_n==2)
{
printf(" 1^ 2^ 3^ 4^ 5^\n");//make sure user knows which dice is which
early = keep_or_not();//ask what dice the user wants to keep
if(early == 1)//if they kept all dice we go score, then return
{
printf("Where would you like to score [ or scratch off ] ?: ");
score();
return early;
}
return early;//if they did NOT keep all dice, early should be 0, the roll is over, so we return
}
if (roll_n==3)//it is the last roll of the turn. nothing to do but score, then return
{
printf("\nWhere would you like to score [ or scratch off ] ?: ");
score();
return early;
}
}
int keep_or_not()
{
int number_held=0;//how many dice has the user decided to keep?
for (dice_n = 1; dice_n <=5 ; dice_n++)
{
printf("for dice %i, keep? (y,Y/n,N or q,Q to quit game.)\n",dice_n);//keep a dice? quit the game?
fflush(stdin);//flush input
char yn;//yes or no
yn = getchar();//lets see what the user picks
if (yn=='q'||yn == 'Q')
{
exit(0);//game over
}
if ((yn == 'y' || yn == 'Y') || ((yn == 'n' || yn == 'N')))//making sure they entered yes or no
{
if (yn == 'y' || yn == 'Y')
{
printf("dice %i held\n",dice_n);
++number_held;//another dice gets held
}
if (yn =='n' || yn=='N')
{
printf("dice %i will be rolled\n",dice_n);
int pass = dice_n;
whatdice(pass);//that dice is rolled
}
}
else//they did not enter yes, no, or quit, so we ask them again for the same dice.
{
--dice_n;
continue;
}
}
if (number_held == 5)
{
return 1;//user kept all dice
}
//user did NOT keep all dice
}
void score()
{
printf("\nUnder Construction, Sorry :-(\n");
if ((dice[0] == dice[1] && dice[2] == dice[3]) && dice[4] == dice[0])//yaht-c!
{
printf("YAHT-C!!!\a\a\a\a\a\n");
}
roll_n = 0;//we are done scoring, so we reset the roll counter
}
void title()
{
int what_title = rnd(6)+1;//two different dice logos based on whether this variable is even or odd
switch (what_title)
{
case 1:
case 3:
case 5:
printf("\a _______ _______ _______ _______ _______ \n| Y || a . || . h || . t-. || . C . |\n| . || || . || || . |\n| || . || . || . . || . . |\n ------- ------- ------- ------- ------- \n");//dice logo if odd
break;
default:
printf("\a _______ _______ _______ _______ _______ \n| . Y || a . || . h . || . t-. || . C . |\n| || . || || . || . . |\n| . || . || . . || . . || . . |\n ------- ------- ------- ------- ------- \n");//dice logo
break;
}
}
-
a == b && b == c && c == d && ... may be written recursively like so:
Code:
int allequal(const int *ptr, size_t n)
{
return n <= 1 ? 1 : ptr[0] == ptr[1] && allequal(ptr + 1, n - 1);
}
edit: By the way, calling fflush with an input stream as its argument has undefined behaviour. You should probably consider another method for reading input. If your program is strictly interactive, you might look at readline (which has nice features like history and stuff) if your implementation provides it.
-
Hmm. Looks like i need to look up pointers. They skimmed over them in the book. Thanks for the tip, Barney!
-
Note the use of tail recursion in Barney McGrew's example. This usually means that it is trivial to replace it with a loop, e.g.,
Code:
int allequal(const int *ptr, size_t n)
{
size_t i;
for (i = 1; i < n; ++i)
{
if (ptr[i - 1] != ptr[i])
{
return 0;
}
}
return 1;
}