programming c++

profileRahanmet
BattleShipGamecodingtemplate.pdf

prog5.cpp

1 /* One-man Battleship Game Akira's Version implementation template. 2 Use -std=c++11 to utilize regex input check. (C) Akira Kawaguchi */ 3 #include <iostream> 4 #include <iomanip> 5 #include <vector> 6 #include <cassert> 7 #include <sstream> 8 #include <algorithm> 9 #include <regex> 10 using namespace std; 11 12 const int DefaultBoardSize = 10; // default board size is 10 x 10. 13 const int DefaultMinShipSize = 2; // default ship size is [2, 4]. 14 const int DefaultMaxShipSize = 4; // 15 const int DefaultShipCount = 6; // defulat ship count in a map is 6. 16 17 enum class Command { INIT, SHOW, QUIT, BOMB }; 18 19 class Cell { 20 enum mark { HIT, MISS, NONE }; 21 mark m_status; // indicating bombed, missed, or not selected. 22 bool m_ship; // indicating presence of ship. 23 public: 24 Cell() : m_status(NONE), m_ship(false) {} 25 26 friend ostream& operator<<(ostream& o, const Cell& c) { 27 switch (c.m_status) { 28 case HIT: o << '@'; break; 29 case MISS: o << '-'; break; 30 case NONE: o << '.'; break; 31 default: assert(false); 32 } 33 return o << ' '; 34 } 35 }; 36 37 class Board { 38 string m_name; // map name. 39 int m_size; // n x n seamap size. 40 vector<vector<Cell> > m_map; // 2D sea map. 41 public: 42 Board(const string& n ="my map", const int s =DefaultBoardSize) : 43 m_name(n), m_size(s) { 44 vector<Cell> a_row(m_size); 45 for (int i = 0; i < m_size; ++i) m_map.push_back(a_row); 46 init(); 47 } 48 void init(const int n =DefaultShipCount) { // randomly set ships in the map. 49 // not implemented. 50 } 51 bool bomb(const int row, const int col) { // bomb the ship! 52 // not implemented. 53 return true; 54 } 55 bool isover() const { 56 // not implemented. 57 return false; 58 } 59 friend ostream& operator<<(ostream& o, const Board& m) { 60 o << " <<" << m.m_name << ">>" << endl << " "; 61 for (int row = 0; row < m.m_size; ++row) o << (char)('A' + row) << ' '; 62 o << endl;

Page 1

prog5.cpp

63 for (int row = 0; row < m.m_size; ++row) { 64 for (int col = 0; col < m.m_size; ++col) { 65 if (!col) o << setw(2) << right << 1 + row << ' '; 66 o << m.m_map[row][col]; 67 } 68 o << endl; 69 } 70 return o; 71 } 72 }; 73 74 /* Input parsing logic for this application. This one uses so-called "regular 75 expressions" to prune out inconsistent input (i.e., syntactic check) at 76 first and then apply more application-related inspections (semantic check). 77 Note that there are three return values - a return value and two non-const 78 references in the parameter list. */ 79 Command parse(const int size, int& row, int& col) { 80 cout << "\nEnter position, \"show\", \"init\" or \"quit\": "; 81 string line; 82 regex pattern1("show|init|quit"); // one word input. 83 regex pattern2("[0-9]+[[:blank:]]+[a-z]"); // two words with space(s) between. 84 85 while (getline(cin, line)) { // read a whole line and convert to lower cases. 86 transform(line.begin(), line.end(), line.begin(), ::tolower); 87 if (regex_match(line, pattern1)) { // match one word input? 88 if (line.find("init") != string::npos) return Command::INIT; 89 if (line.find("show") != string::npos) return Command::SHOW; 90 if (line.find("quit") != string::npos) return Command::QUIT; 91 } // you can use enum if you want above instead of a number return. 92 if (regex_match(line, pattern2)) { // match two word input? 93 string c, r; 94 istringstream iss(line); // then read int two words. 95 iss >> c >> r; // stringstream is the one to use! 96 assert(!iss.fail()); // this will not happen (why?) 97 row = atoi(c.c_str()) - 1; // apply semantic check for col, 98 col = r[0] - 'a'; // and row values. 99 if (row >= 0 && row < size && col >= 0 && col < size) 100 return Command::BOMB; 101 } 102 cout << "Input error, try again: "; 103 } 104 assert(false); // to make sure not to reach here. 105 } 106 107 int main() { 108 const int size = DefaultBoardSize; // instantiate a board object with 109 Board b("Pacific Ocean", size); // game (war) name and board size. 110 111 while (true) { 112 cout << b; 113 114 int row, col; 115 switch (parse(size, row, col)) { 116 case Command::QUIT: goto END; // "quit" is to end the game. 117 case Command::SHOW: break; // "show" is to show the answer. 118 case Command::INIT: b.init(); continue; // "init" is to restart the game. 119 case Command::BOMB: break; // other correct input. 120 default: abort(); // should not reach. 121 } 122 bool r = b.bomb(row, col); // otherwise do the game... 123 cout << "You " << (r? "\ahit :)" : "missed :(") << endl; 124 if (b.isover()) {

Page 2

prog5.cpp

125 cout << "You bombed all ships, congratulations!" << endl; 126 break; 127 } 128 } 129 END: 130 cout << "Bye..." << endl; 131 return 0; 132 } 133

Page 3