Advertisement
cd62131

blackjack.c

Oct 24th, 2013
214
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C 5.40 KB | None | 0 0
  1. #include "blackjack.h"
  2.  
  3. extern card_t *cards;
  4. char * const suits[] = { "Spade", "Heart", "Diamond", "Club" };
  5. char * const face[] = {
  6.   "dummy", "A", "2", "3", "4", "5", "6", "7", "8", "9", "10", "J", "Q", "K" };
  7.  
  8. fighter_t *new_fighter(void) {
  9.   fighter_t * new = (fighter_t *) malloc(sizeof(fighter_t));
  10.   new->value = 0;
  11.   new->card = (card_t *) NULL;
  12.   new->prev = (fighter_t *) NULL;
  13.   return new;
  14. }
  15.  
  16. void init_cards(void) {
  17.   cards = (card_t *) malloc(sizeof(card_t) * DECK * 4 * 13);
  18.   int count = 0;
  19.   for (int i = 0; i < DECK; i++) {
  20.     for (int j = 0; j < 4; j++) {
  21.       for (int k = 1; k <= 13; k++) {
  22.         cards[count].suit = suits[j];
  23.         cards[count].face = face[k];
  24.         cards[count].kind = k;
  25.         if (k == 1) cards[count].worth = 11;
  26.         else if (k < 10) cards[count].worth = k;
  27.         else cards[count].worth = 10;
  28.         count++;
  29.       }
  30.     }
  31.   }
  32.   shuffle();
  33. }
  34.  
  35. void shuffle(void) {
  36.   srand((unsigned int) time(NULL));
  37.   for (int i = DECK * 4 * 13 - 1; i > 0; i--) {
  38.     int random = rand() % i;
  39.     card_t swap = cards[i];
  40.     cards[i] = cards[random];
  41.     cards[random] = swap;
  42.   }
  43. }
  44.  
  45. card_t *pull_card(void) {
  46.   static int front = 0;
  47.   return &cards[front++];
  48. }
  49.  
  50. fighter_t *new_state(fighter_t *fighter, card_t *card) {
  51.   fighter_t *new = new_fighter();
  52.   new->prev = fighter;
  53.   new->value = fighter->value + card->worth;
  54.   new->card = (card_t *) malloc(sizeof(card_t));
  55.   new->card->suit = card->suit;
  56.   new->card->face = card->face;
  57.   new->card->kind = card->kind;
  58.   new->card->worth = card->worth;
  59.   return new;
  60. }
  61.  
  62. void print_fight_without_hole(fighter_t *dealer, fighter_t *player) {
  63.   printf("Dealer up cards: ");
  64.   print_up(dealer);
  65.   puts("");
  66.   print_player(player);
  67. }
  68.  
  69. void print_up(fighter_t *dealer) {
  70.   for (fighter_t *p = dealer; p->prev->prev != NULL; p = p->prev) {
  71.     printf("%s %s", p->card->suit, p->card->face);
  72.     if (p->prev->prev->prev != NULL) printf(", ");
  73.   }
  74. }
  75.  
  76. void print_player(fighter_t *player) {
  77.   printf("Player value: %i, cards: ", player->value);
  78.   print_hand(player);
  79.   puts("");
  80. }
  81.  
  82. void print_hand(fighter_t *fighter) {
  83.   for (fighter_t *p = fighter; p->prev != NULL; p = p->prev) {
  84.     printf("%s %s", p->card->suit, p->card->face);
  85.     if (p->prev->prev != NULL) printf(", ");
  86.   }
  87. }
  88.  
  89. void print_fight(fighter_t *dealer, fighter_t *player) {
  90.   if (dealer->value > 21) puts("Dealer Bust");
  91.   else if (player->value > 21) puts("You Bust");
  92.   else if (dealer->value == player->value) puts("Even");
  93.   else if (player->value == 21) puts("You Blackjack");
  94.   else if (dealer->value == 21) puts("Dealer Blackjack");
  95.   else if (dealer->value > player->value) puts("You Lose");
  96.   else if (dealer->value < player->value) puts("You Win");
  97.   else puts("Even");
  98.   printf("Dealer value: %i, cards: ", dealer->value);
  99.   print_hand(dealer);
  100.   puts("");
  101.   print_player(player);
  102. }
  103.  
  104. judge_t judge(fighter_t *dealer, fighter_t *player) {
  105.   if (dealer->value == 21 && player->value == 21) return Even;
  106.   if (dealer->value == 21) return DealerBlackjack;
  107.   if (dealer->value < 17) return DealerDuty;
  108.   if (dealer->value >= 17 && dealer->value < 21) return DealerPass;
  109.   if (dealer->value > 21) return DealerBust;
  110.   if (player->value == 21) return PlayerBlackjack;
  111.   if (player->value > 21) return PlayerBust;
  112.   return HitOrStay;
  113. }
  114.  
  115. fighter_t *pull(fighter_t *fighter) {
  116.   card_t *card = pull_card();
  117.   return new_state(fighter, card);
  118. }
  119.  
  120. fighter_t *try_soft_ace(fighter_t *fighter) {
  121.   for (fighter_t *p = fighter; p->prev != NULL; p = p->prev) {
  122.     if (p->card->kind != Ace) continue;
  123.     p->card->kind = One;
  124.     fighter->value -= 10;
  125.     puts("TrySoftAce");
  126.     return fighter;
  127.   }
  128.   return fighter;
  129. }
  130.  
  131. fighter_t *hit_or_stay(fighter_t *player) {
  132.   int n;
  133.   char *yes_or_no = NULL;
  134.   printf("Hit? (y/n); ");
  135.   n = scanf("%ms", &yes_or_no);
  136.   if (n != 1) exit(1);
  137.   if (strcmp(yes_or_no, "y")) return player;
  138.   return pull(player);
  139. }
  140.  
  141. int count_ace(fighter_t *fighter) {
  142.   int count = 0;
  143.   for (fighter_t *p = fighter; p->prev != NULL; p = p->prev) {
  144.     if (p->card->kind == Ace) count++;
  145.   }
  146.   return count;
  147. }
  148.  
  149. int main(int ac, char **av) {
  150.   puts("Blackjack");
  151.  
  152.   init_cards();
  153.  
  154.   fighter_t *dealer = new_fighter();
  155.   fighter_t *player = new_fighter();
  156.  
  157.   for (int i = 0; i < 2; i++) {
  158.     card_t *card = pull_card();
  159.     player = new_state(player, card);
  160.     card = pull_card();
  161.     dealer = new_state(dealer, card);
  162.   }
  163.  
  164.   while (1) {
  165.     fighter_t *same = NULL;
  166.     print_fight_without_hole(dealer, player);
  167.     switch (judge(dealer, player)) {
  168.     case DealerBust:
  169.       if (count_ace(dealer) > 0) {
  170.         dealer = try_soft_ace(dealer);
  171.         continue;
  172.       } // wall through
  173.     case DealerBlackjack:
  174.     case PlayerBlackjack:
  175.     case Even:
  176.       print_fight(dealer, player);
  177.       exit(0);
  178.       break;
  179.     case PlayerBust:
  180.       if (count_ace(player) > 0) {
  181.         player = try_soft_ace(player);
  182.         continue;
  183.       }
  184.       print_fight(dealer, player);
  185.       exit(0);
  186.       break;
  187.     case DealerDuty:
  188.       puts("Dealer Duty");
  189.       dealer = pull(dealer);
  190.       break;
  191.     case HitOrStay:
  192.       pull(dealer); // walk through
  193.     case DealerPass:
  194.       same = player;
  195.       player = hit_or_stay(player);
  196.       if (player != same) continue;
  197.       print_fight(dealer, player);
  198.       exit(0);
  199.       break;
  200.     default:
  201.       break;
  202.     }
  203.   }
  204. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement