Hydreigon_Lord

Pair Game

May 4th, 2020
152
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 7.18 KB | None | 0 0
  1. //Hydreigon_Lord
  2. //Pair Game
  3. /*
  4.  IF YOU ARE GETTING AN ERROR:
  5.  Exit Code 16: Make sure the contestant file exists and is accessible.
  6.  Exit Code 17: Make sure the contestant file contains at least NUM_CONTESTANTS contestants (one contestant per line).
  7.  Exit Code 32: Make sure the card file exists and is accessible.
  8.  Exit Code 33: Make sure the card file contains at least NUM_CARD_TYPES cards (one card per line).
  9.  Exit Code 48: Make sure you are not entering the name of a read-only file when asked for an output filename.
  10.  */
  11.  
  12. #include <iostream>
  13. #include <fstream>
  14. #include <string>
  15. #include <ctime>
  16. using namespace std;
  17.  
  18. const int NUM_CONTESTANTS = 26;
  19. const int NUM_CARD_TYPES = 13;
  20. const string CONTESTANT_FILENAME = "contestants.txt";
  21. const string CARD_FILENAME = "cards.txt";
  22.  
  23. class Contestant
  24. {
  25. private:
  26.     string name, card1, card2;
  27. public:
  28.     Contestant() {name = ""; card1 = ""; card2 = "";};
  29.     void setName(string n) {name = n;};
  30.     void setCard1(string c1) {card1 = c1;};
  31.     void setCard2(string c2) {card2 = c2;};
  32.     string getName() const {return name;};
  33.     string getCard1() const {return card1;};
  34.     string getCard2() const {return card2;};
  35.     bool hasPair() const {return card1 == card2;};
  36.     operator string() const {return name + ": " + card1 + ", " + card2 + (hasPair() ? " (pair)" : "");}
  37. };
  38.  
  39. //Canonical implementation of overloaded stream insertion from cppreference.com
  40. std::ostream& operator<<(std::ostream& os, const Contestant& obj)
  41. {
  42.     os << (string)obj;
  43.     return os;
  44. }
  45.  
  46. int main()
  47. {
  48.     static_assert(NUM_CONTESTANTS > 0 && NUM_CARD_TYPES > 0 && NUM_CONTESTANTS % NUM_CARD_TYPES == 0, "Invalid game parameters; check values of NUM_CONTESTANTS and NUM_CARD_TYPES");
  49.     int cardCopies = NUM_CONTESTANTS / NUM_CARD_TYPES * 2;
  50.    
  51.     //Read the contestant and card lists from the respective files
  52.     //The files should contain one contestant or card per line
  53.     fstream contin(CONTESTANT_FILENAME, ios::in), cardin(CARD_FILENAME, ios::in);
  54.     if (!contin)
  55.     {
  56.         cout << "Error reading file " << CONTESTANT_FILENAME << endl;
  57.         exit(1 << 4);
  58.     }
  59.     if (!cardin)
  60.     {
  61.         cout << "Error reading file " << CARD_FILENAME << endl;
  62.         exit(2 << 4);
  63.     }
  64.     Contestant* conts = new Contestant[NUM_CONTESTANTS];
  65.     string* cards = new string[NUM_CONTESTANTS * 2];
  66.     for (int i = 0; i < NUM_CONTESTANTS; i++)
  67.     {
  68.         string name;
  69.         if (contin.eof())
  70.         {
  71.             cout << "Unexpected EOF reading file " << CONTESTANT_FILENAME << endl;
  72.             exit((1 << 4) + 1);
  73.         }
  74.         else
  75.         {
  76.             getline(contin, name);
  77.             conts[i].setName(name);
  78.         }
  79.     }
  80.     for (int i = 0; i < NUM_CARD_TYPES; i++)
  81.     {
  82.         string card;
  83.         if (cardin.eof())
  84.         {
  85.             cout << "Unexpected EOF reading file " << CARD_FILENAME << endl;
  86.             exit((2 << 4) + 1);
  87.         }
  88.         else
  89.         {
  90.             getline(cardin, card);
  91.             for (int j = 0; j < cardCopies; j++)
  92.                 cards[i * cardCopies + j] = card;
  93.         }
  94.     }
  95.     cout << "Successfully read files.\n";
  96.     contin.close();
  97.     cardin.close();
  98.    
  99.     //Ask the user for a file to output the game report to
  100.     string outFileName;
  101.     cout << "Enter the output filename: ";
  102.     cin >> outFileName;
  103.     fstream fout(outFileName, ios::out);
  104.     fout << "*** Pair Game Report ***\n\n\n";
  105.     if (!fout)
  106.     {
  107.         cout << "Error writing to file " << outFileName << endl;
  108.         exit(3 << 4);
  109.     }
  110.     cout << "Successfully opened file for writing.\n";
  111.    
  112.     //Declare other game-related variables
  113.     bool* finished = new bool[NUM_CONTESTANTS];
  114.     for (int i = 0; i < NUM_CONTESTANTS; i++)
  115.         finished[i] = false;
  116.     int* finishRounds = new int[NUM_CONTESTANTS];
  117.     int numFinished = 0;
  118.     int round = 0;
  119.    
  120.     //Shuffle the cards
  121.     srand(time(0));
  122.     for (int i = 0; i < NUM_CONTESTANTS * 2; i++)
  123.     {
  124.         int j = rand() % (NUM_CONTESTANTS * 2);
  125.         string temp = cards[i];
  126.         cards[i] = cards[j];
  127.         cards[j] = temp;
  128.     }
  129.    
  130.     //Deal the cards
  131.     for (int i = 0; i < NUM_CONTESTANTS; i++)
  132.     {
  133.         conts[i].setCard1(cards[2 * i]);
  134.         conts[i].setCard2(cards[2 * i + 1]);
  135.     }
  136.    
  137.     //Play the game
  138.     do
  139.     {
  140.         round++;
  141.         fout << "=== Round " << round << " ===\n\n";
  142.         //Output each contestant's hand and detect pairs
  143.         fout << "--- Contestant Hands ---\n";
  144.         for (int i = 0; i < NUM_CONTESTANTS; i++)
  145.         {
  146.             if (!finished[i])
  147.             {
  148.                 fout << conts[i] << endl;
  149.                 if (conts[i].hasPair())
  150.                 {
  151.                     finished[i] = true;
  152.                     finishRounds[i] = round;
  153.                     numFinished++;
  154.                 }
  155.             }
  156.         }
  157.         fout << endl;
  158.         if (numFinished == NUM_CONTESTANTS)
  159.         {
  160.             cout << "Game complete.\n";
  161.             break;
  162.         }
  163.         //Have each contestant who has not finished pass a card
  164.         fout << "--- Passing ---\n";
  165.         int firstCont = -1, prevCont = -1;
  166.         string prevCard = "", currCard = "";
  167.         bool firstPassCard1 = true, passCard1 = true;
  168.         for (int i = 0; i < NUM_CONTESTANTS; i++)
  169.         {
  170.             if (!finished[i])
  171.             {
  172.                 passCard1 = rand() % 2;
  173.                 if (firstCont == -1)
  174.                 {
  175.                     firstCont = i;
  176.                     if (passCard1)
  177.                         prevCard = conts[i].getCard1();
  178.                     else
  179.                         prevCard = conts[i].getCard2();
  180.                     firstPassCard1 = passCard1;
  181.                 }
  182.                 else
  183.                 {
  184.                     if (passCard1)
  185.                     {
  186.                         currCard = conts[i].getCard1();
  187.                         conts[i].setCard1(prevCard);
  188.                     }
  189.                     else
  190.                     {
  191.                         currCard = conts[i].getCard2();
  192.                         conts[i].setCard2(prevCard);
  193.                     }
  194.                     fout << conts[prevCont].getName() << " passes " << prevCard << " to " << conts[i].getName() << endl;
  195.                     prevCard = currCard;
  196.                 }
  197.                 prevCont = i;
  198.             }
  199.         }
  200.         if (firstPassCard1)
  201.             conts[firstCont].setCard1(prevCard);
  202.         else
  203.             conts[firstCont].setCard2(prevCard);
  204.         fout << conts[prevCont].getName() << " passes " << prevCard << " to " << conts[firstCont].getName() << "\n\n";
  205.         cout << "Wrote round " << round << "; " << (NUM_CONTESTANTS - numFinished) << " contestants remain.\n";
  206.     }
  207.     while (numFinished < NUM_CONTESTANTS);
  208.    
  209.     //Report how many rounds it took each contestant to finish
  210.     fout << "=== Final Results ===\n\n";
  211.     for (int i = 0; i < NUM_CONTESTANTS; i++)
  212.         fout << conts[i].getName() << " finished on round " << finishRounds[i] << endl;
  213.    
  214.     //Cleanup
  215.     fout.close();
  216.     delete[] conts;
  217.     delete[] cards;
  218.     delete[] finished;
  219.     delete[] finishRounds;
  220.     return 0;
  221. }
Add Comment
Please, Sign In to add comment