Quantcast

Jump to content

» «
Photo

[WIP][C++] Blackjack

6 replies to this topic
Tornado Rex
  • Tornado Rex

    *nix gets the chicks

  • $outh $ide Hoodz
  • Joined: 12 Nov 2001

#1

Posted 26 April 2005 - 11:22 AM Edited by Tornado Rex, 26 April 2005 - 02:50 PM.

So I got f*cking bored the other night and thought to myself:
QUOTE (Self)
Hey, I haven't coded C++ lately. I wonder if I still remember.

So I decided to make a blackjack program (figured it uses a lot of stuff I used to know). I started going to town. Here's where I'm at now:
CODE
#include <iostream>
#include <cmath>
using namespace std;

/* Functions */
void init();
void deal();
void display();
void pformat(int card, int num);
void dformat(int card, int num);
int dealercard(int x);
int playercard(int x);

/* Globals */
int deck[51];
int ptotal = 0;
int dtotal = 0;
int pcard[25];
int dcard[25];
char pdisplay[25];
char ddisplay[25];
int pc[25];
int dc[25];

CODE
int main() {

srand((unsigned)time(0));
/* Let's get a REAL deck eh? */
init();

/* K done. Now to deal the cards */
deal();

/* We need to display everything! */
display();

return 0;}

CODE
void init() {

int z = 0;

/* First we have to get all of our 10s */
for (int i = 0;i < 16;i++)
 deck[i] = 10;
 
/* K sweet. Now we have to get 1 through 9 (we'll get 11 in there later, don't worry) */
for (int x = 1;x < 10;x++) {
 for (int y = 0;y < 4;y++) {
  z++;
  deck[15+z] = x;}}}

CODE
void deal() {
int y = 0;
int z = 0;

/* We gotta give the players alternating cards. It's teh r00lz!
  We gonna do it like this: If the number is even, card goes to dealer.
  If odd, card goes to player (that way player gets the first card) */
for (int x = 1;x < 5;x++) {
 if (x%2 != 0) {
  playercard(y);
  y++;}
 else {
  dealercard(z);
  z++;}}
 
}

CODE
int playercard(int x) {
/* We need some sh*t declared here */
int ace = 0;
int y = rand()%51+0;

/* Now we have to get a card from the deck and check whether it's
  taken (by seeing if the value is 0). */
  while (deck[y] == 0)
 pcard[x] = deck[y];

pformat(y,x);

/* Now we have to set the deck card value to 0 (for other checks) */
deck[y] = 0;

/* Now we have to add our card to our total */
ptotal += pcard[x];

/* Alrighty. Let's check if we got an Ace (1). Why is this you ask?
  Well Ace is either 11 OR 1. We have to see if adding 11 to our total
  will put us over. If it won't, we add it. If it will, we don't.
  This will actually get really complicated. If we get an Ace on the
  first card it will be 11. If we then got, say, a seven we have a
  total of 18. If we hit and get a four our total will be 22. sh*t!
  We'll get to that in a second. First lets see if it's an Ace and
  can be used as 11. If it can, we add 10 to it. We're also going to
  keep track of how many Aces we have. */
if ((pcard[x] == 1) && ((ptotal + 11) < 22)) {
pcard[x] = 11;
ptotal += pcard[x];
ace++;}

/* Now we have to see whether a previous ace put us over. If it did
  we will subtract 10 from the player's total. */
if ((ptotal > 21) && ace)
 ptotal -= 10;

/* Now we return ptotal. */
/* Note: We return ptotal every time but it doesn't matter because
  we only call it when it's the actual total */
return ptotal;}

CODE
int dealercard(int x) {
/* We need some sh*t declared here */
int ace = 0;
int y = rand()%51+0;

/* Now we have to get a card from the deck and check whether it's
  taken (by seeing if the value is 0). */
while (deck[y] == 0)
 dcard[x] = deck[y];

/* Now we have to add our card to our total */
dtotal += dcard[x];

/* We gotta make the cards look pretty */
dformat(y,x);

/* Now we have to set the deck card value to 0 (for other checks) */
deck[y] = 0;

/* Alrighty. Let's check if we got an Ace (1). Why is this you ask?
  Well Ace is either 11 OR 1. We have to see if adding 11 to our total
  will put us over. If it won't, we add it. If it will, we don't.
  However, if we get an Ace on the first card it will be 11. If we
  then got, say, a seven we have a total of 18. If we hit and get
  a four our total will be 22. sh*t! We'll get to that in a second.
  First lets see if it's an Ace and can be used as 11. If it can, we
  add 10 to it. We're also going to  keep track of how many Aces we have. */
if ((dcard[x] == 1) && ((dtotal + 11) < 22)) {
dcard[x] = 11;
dtotal += dcard[x];
ace++;}

/* Now we have to see whether a previous ace put us over. If it did
  we will subtract 10 from the player's total. */
if ((dtotal > 21) && ace)
 dtotal -= 10;

/* Now we return dtotal. */
/* Note: We return dtotal every time but it doesn't matter because
  we only call it when it's the actual total */
return dtotal;}

CODE
void pformat(int card, int num) {
for (int i = 0;i < 25;i++)
 pc[i] = 0;
/* Player check */
if (card < 4) {
 pdisplay[num] = 'K';
 pc[num] = 1;}
else if ((card < 8) && (card > 3)) {
 pdisplay[num] = 'Q';
 pc[num] = 1;}
else if ((card < 12) && (card > 7)) {
 pdisplay[num] = 'J';
 pc[num] = 1;}
else
 pcard[num] = deck[num];
}

CODE
void dformat(int card, int num) {
for (int i = 0;i < 25;i++)
 dc[i] = 0;
/* Dealer check */
if (card < 4) {
 ddisplay[num] = 'K';
 dc[num] = 1;}
else if ((card < 8) && (card > 3)) {
 ddisplay[num] = 'Q';
 dc[num] = 1;}
else if ((card < 12) && (card > 7)) {
 ddisplay[num] = 'J';
 dc[num] = 1;}
else
 dcard[num] = deck[num];
}

CODE
void display() {
cout << "Player has: ";
for (int i = 0;i < 2;i++) {
 if (pc[i] == 1)
  cout << pdisplay[i] << " ";
 else
  cout << pcard[i] << " ";}
cout << endl;
cout << "Dlayer has: ";
for (int i = 0;i < 2;i++){
 if (dc[i] == 1)
  cout << ddisplay[i] << " ";
 else
  cout << dcard[i] << " ";}
cout << endl;
}


Now, as you may be able to tell. You can't do anything yet. It displays the 2 cards that the player and dealer get on the deal. That's it for now.

Now you may be saying to yourself:
QUOTE (You)
What the f*ck is the point of that!? I can't even play it and you're releasing it!?

Well, I'm stuck. Like I said before, I haven't coded C++ in a long time.

I come to you oh coding gurus of GTAF for help. WTF is wrong? When I run it, it doesn't seem to work right. I get a lot of 10's, face cards (which is to be expected I suppose), some 0s, and sometimes it seems to just get stuck in a loop.

So please. If you have any ideas as to why it's all f*cked up. Please do help.

P.S. If you need me to host a compiled .exe I can, though I don't know why anyone would need one if they have a compiler. Just let me know if you need one.

And ty in advance for any help you give. If I get no help: f*ck you all mad.gif

biggrin.gif

Btw. Sorry for the long ass code. I like my code in a certain way and didn't feel like re-formatting it to post here.

Here's a text file of the code (copy and save as .cpp) for all you who don't want to copy each function smile.gif omg blackjack.txt

Knightmare
  • Knightmare

    man tongues

  • $outh $ide Hoodz
  • Joined: 18 Nov 2001

#2

Posted 26 April 2005 - 01:45 PM

CODE
if ((ptotal > 21) && ace)
ptotal -= 10;


So you're checking if the total is over 21, and if you have an ace here? When someone has an ace, that variable gets changed to 1, correct? Since ace is an int then maybe it should be changed to:

CODE
if((ptotal>21) && (ace==1)
ptotal-=10;


I'll check over it in more detail later, can you host the .exe? I don't have a compiler at home.

Edit: Thanks for the nice big block of code tounge.gif If you are bored maybe split the functions into different code tables?

Tornado Rex
  • Tornado Rex

    *nix gets the chicks

  • $outh $ide Hoodz
  • Joined: 12 Nov 2001

#3

Posted 26 April 2005 - 02:01 PM Edited by Tornado Rex, 26 April 2005 - 02:09 PM.

QUOTE (Knightmare @ Apr 26 2005, 08:45)
CODE
if ((ptotal > 21) && ace)
ptotal -= 10;


So you're checking if the total is over 21, and if you have an ace here?  When someone has an ace, that variable gets changed to 1, correct?  Since ace is an int then maybe it should be changed to:

CODE
if((ptotal>21) && (ace==1)
ptotal-=10;

Well, those two codes do the same thing. Mine just says 'and ace is true' (basically not 0).

Also, apparently the .exe I compile can't be run alone. *shrug* If someone would be nice enough to compile me one I can host and everything.

Mmk all edited for ya Knight smile.gif

Svip
  • Svip

    I eat babies

  • The Connection
  • Joined: 12 Nov 2001
  • None

#4

Posted 26 April 2005 - 02:37 PM

Pfft, why did you seperate each function in it's one code tag?

Why not make some lines or nothing?

( lines
CODE
=============================
)

Just so I could copy it right away.

I don't wanna sit and copy all that now. sad.gif

But looks great.

Tornado Rex
  • Tornado Rex

    *nix gets the chicks

  • $outh $ide Hoodz
  • Joined: 12 Nov 2001

#5

Posted 26 April 2005 - 02:48 PM Edited by Tornado Rex, 26 April 2005 - 02:58 PM.

blackjack.txt <--- text file of the code (for you Svippers wink.gif ).

Edit:
Here are some outputs I got (since I don't have the .exe up yet).

CODE
Player has: 10 K
Dealer has: 10 10
Press any key to continue...


CODE
Player has: 0 10
Dealer has: 10 10
Press any key to continue...


etc. They just have different varriants of that pretty much (just 10s, 0s, and face cards though).

Svip
  • Svip

    I eat babies

  • The Connection
  • Joined: 12 Nov 2001
  • None

#6

Posted 26 April 2005 - 03:52 PM Edited by Svip, 26 April 2005 - 04:46 PM.

Could it be because of the script that checks if it's 11 OR 1?

I'm looking through your code... can't seem to find it.

But what I wonder is if it could be easier to write, and maybe shorter.

Cause it seems like a lot of mess ( with all those comments ) for such a simple game.

You basically have to do following at first;

A. Player gets a random card between 1 and 13.

B. The value of the card is then removed from the deck. So deck[value] = 0;

C. Dealer is given the same.

D. Both players get another card with the same rutine.

E. Okay, if the card's value is 11, then J, if 12 then Q, if 13 then R.

F. Display that.

Simple rutine. Now after that there should be a function allowing the player to stick/stop.

I think I'll try and write that.

Hold on...

EDIT: Okay here is a code that does exact same as your's ( displaying the cards ):
CODE
#include <iostream>
#include <stdio.h>
#include <cmath>
#include <time.h>

//Functions
void display();

//Globals...
int plcard[2][12];
int cards[13] = { 4,4,4,4,4,4,4,4,4,4,4,4,4 };

int main() {
srand(time(NULL));
//Note; this will be placed inside a function later, but now it's just cool this way.
plcard[0][0] = rand()%12+1;
cards[plcard[0][0] - 1] -= 1;
plcard[1][0] = rand()%12+1;
cards[plcard[1][0] - 1] -= 1;
plcard[0][1] = rand()%12+1;
cards[plcard[0][1] - 1] -= 1;
plcard[1][1] = rand()%12+1;
cards[plcard[1][1] - 1] -= 1;
display();
return 0;
}

void display() {
int i,j;
for (i = 0;i <= 1; i++) {
 if (i == 0) { printf("Player has: "); }
 else if (i == 1) { printf("Dealer has: "); }
 for (j = 0;j <= 11;j++) {
  if (plcard[i][j] == 13) {
   printf("R ");
  }
  else if (plcard[i][j] == 12) {
   printf("Q ");
  }
  else if (plcard[i][j] == 11) {
   printf("J ");
  }
  else if ((plcard[i][j] >= 1) && (plcard[i][j] < 11)) {
   printf("%d ", plcard[i][j]);
  }
 }
 printf("\n");
}
}

And it has no bug about 10s. Currently it just graps the random number and displays it for the user, as I am unsure how that 11 or 1 works in blackjac.

PatrickW
  • PatrickW

    GTA Juggernaut

  • The Connection
  • Joined: 07 Jan 2004
  • Netherlands
  • Best Script 2013 [DYOM]
    Best Script 2012 [DYOM]

#7

Posted 26 April 2005 - 08:32 PM

This is hardly to be called C++.. The only C++ features that you use is the iostreams.
So this is basicly a C program.

As Svip showed, this could all be coded much more efficient. The fact that de playercard and dealercard functions are almost the same, should give you a clue of things to be optimised... same for the pformat and dformat functions.

Anyway, you should be able to get this running also.... I added comments in red to your source.. These should fix the problems you signaled.


QUOTE (Tornado Rex @ Apr 26 2005, 13:22)
#include <iostream>
#include <cmath>
using namespace std;

/* Functions */
void init();
void deal();
void display();
void pformat(int card, int num);
void dformat(int card, int num);
int dealercard(int x);
int playercard(int x);

/* Globals */
int deck[51];  /* You really need 52 here, than the indexes go from 0 .. 51 */
int ptotal = 0;
int dtotal = 0;
int pcard[25];
int dcard[25];
char pdisplay[25];
char ddisplay[25];
int pc[25];
int dc[25];

int main() {

srand((unsigned)time(0));
/* Let's get a REAL deck eh? */
init();

/* K done. Now to deal the cards */
deal();

/* We need to display everything! */
display();

return 0;}
void init() {

int z = 0;

/* First we have to get all of our 10s */
for (int i = 0;i < 16;i++)
  deck[i] = 10;
 
/* K sweet. Now we have to get 1 through 9 (we'll get 11 in there later, don't worry) */
for (int x = 1;x < 10;x++) {
  for (int y = 0;y < 4;y++) {
  z++;
  deck[15+z] = x;}}}
void deal() {
int y = 0;
int z = 0;

/* We gotta give the players alternating cards. It's teh r00lz!
  We gonna do it like this: If the number is even, card goes to dealer.
  If odd, card goes to player (that way player gets the first card) */

/* This for loop should be a while loop, that deals card until either one has more than 21 */
for (int x = 1;x < 5;x++) {
  if (x%2 != 0) {
  playercard(y);
  y++;}
  else {
  dealercard(z);
  z++;}}
 
}
int playercard(int x) {
/* We need some sh*t declared here */
int ace = 0;
int y = rand()%51+0;    /* This also needs to be 52 */

/* Now we have to get a card from the deck and check whether it's
  taken (by seeing if the value is 0). */

  /* This WHILE loop will never end if you ever get in the deck[y] == 0 situation */
    * while (deck[y] == 0)
    *pcard[x] = deck[y];
    */
    while (deck[y] == 0 ) y = rand()%52;

    pcard[x] = deck[y];
pformat(y,x);

/* Now we have to set the deck card value to 0 (for other checks) */
deck[y] = 0;

/* Now we have to add our card to our total */
ptotal += pcard[x];

/* Alrighty. Let's check if we got an Ace (1). Why is this you ask?
  Well Ace is either 11 OR 1. We have to see if adding 11 to our total
  will put us over. If it won't, we add it. If it will, we don't.
  This will actually get really complicated. If we get an Ace on the
  first card it will be 11. If we then got, say, a seven we have a
  total of 18. If we hit and get a four our total will be 22. sh*t!
  We'll get to that in a second. First lets see if it's an Ace and
  can be used as 11. If it can, we add 10 to it. We're also going to
  keep track of how many Aces we have. */
if ((pcard[x] == 1) && ((ptotal + 11) < 22)) {
pcard[x] = 11;
ptotal += pcard[x]; /* ptotal += 10...... you already added the 1 above */
ace++;}

/* Now we have to see whether a previous ace put us over. If it did
  we will subtract 10 from the player's total. */
if ((ptotal > 21) && ace)
  ptotal -= 10;  /* You also need to ace--, otherwise you'll use the ace multiple times */

/* Now we return ptotal. */
/* Note: We return ptotal every time but it doesn't matter because
  we only call it when it's the actual total */
return ptotal;}


/* same comments for dealercard as for playercard */
int dealercard(int x) {
/* We need some sh*t declared here */
int ace = 0;
int y = rand()%51+0;

/* Now we have to get a card from the deck and check whether it's
  taken (by seeing if the value is 0). */
while (deck[y] == 0)
  dcard[x] = deck[y];

/* Now we have to add our card to our total */
dtotal += dcard[x];

/* We gotta make the cards look pretty */
dformat(y,x);

/* Now we have to set the deck card value to 0 (for other checks) */
deck[y] = 0;

/* Alrighty. Let's check if we got an Ace (1). Why is this you ask?
  Well Ace is either 11 OR 1. We have to see if adding 11 to our total
  will put us over. If it won't, we add it. If it will, we don't.
  However, if we get an Ace on the first card it will be 11. If we
  then got, say, a seven we have a total of 18. If we hit and get
  a four our total will be 22. sh*t! We'll get to that in a second.
  First lets see if it's an Ace and can be used as 11. If it can, we
  add 10 to it. We're also going to  keep track of how many Aces we have. */
if ((dcard[x] == 1) && ((dtotal + 11) < 22)) {
dcard[x] = 11;
dtotal += dcard[x];
ace++;}

/* Now we have to see whether a previous ace put us over. If it did
  we will subtract 10 from the player's total. */
if ((dtotal > 21) && ace)
  dtotal -= 10;

/* Now we return dtotal. */
/* Note: We return dtotal every time but it doesn't matter because
  we only call it when it's the actual total */
return dtotal;}
void pformat(int card, int num) {
for (int i = 0;i < 25;i++)
  pc[i] = 0;
/* Player check */
if (card < 4) {
  pdisplay[num] = 'K';
  pc[num] = 1;}
else if ((card < 8) && (card > 3)) {
  pdisplay[num] = 'Q';
  pc[num] = 1;}
else if ((card < 12) && (card > 7)) {
  pdisplay[num] = 'J';
  pc[num] = 1;}
else
  pcard[num] = deck[num];    /* This is the reasons for all the 10's */
                                            /* it should be pcard[num] = deck[card];*/

}
void dformat(int card, int num) {
for (int i = 0;i < 25;i++)
  dc[i] = 0;
/* Dealer check */
if (card < 4) {
  ddisplay[num] = 'K';
  dc[num] = 1;}
else if ((card < 8) && (card > 3)) {
  ddisplay[num] = 'Q';
  dc[num] = 1;}
else if ((card < 12) && (card > 7)) {
  ddisplay[num] = 'J';
  dc[num] = 1;}
else
  dcard[num] = deck[num];    /* This is the reasons for all the 10's */
                                            /* it should be pcard[num] = deck[card];*/

}
void display() {
cout << "Player has: ";
for (int i = 0;i < 2;i++) {
  if (pc[i] == 1)
  cout << pdisplay[i] << " ";
  else
  cout << pcard[i] << " ";}
cout << endl;
cout << "Dlayer has: ";
for (int i = 0;i < 2;i++){
  if (dc[i] == 1)
  cout << ddisplay[i] << " ";
  else
  cout << dcard[i] << " ";}
cout << endl;
}





1 user(s) are reading this topic

0 members, 1 guests, 0 anonymous users