This commit is contained in:
Sandipsinh Rathod 2024-11-19 19:11:06 -05:00
parent f99efc4208
commit 273662fde0
10 changed files with 61 additions and 44 deletions

@ -13,4 +13,5 @@ add_executable(hw4 main.cpp
strategic_player.cpp strategic_player.cpp
gameplay.cpp gameplay.cpp
gameplay.cpp gameplay.cpp
player.h) player.h
io.cpp)

@ -13,15 +13,15 @@ Gameplay::~Gameplay() {
} }
void Gameplay::playGame() { void Gameplay::playGame() {
std::ofstream outputFile("output.txt"); ofstream outputFile("output.txt");
if (!outputFile) { if (!outputFile) {
std::cerr << "Error: Could not open output file for writing." << std::endl; cerr << "Error: Could not open output file for writing." << endl;
return; return;
} }
// Write board dimensions to the output file // Write board dimensions to the output file
outputFile << board.getRows() << " " << board.getCols() << std::endl; outputFile << board.getRows() << " " << board.getCols() << endl;
std::cout << board.getRows() << " " << board.getCols() << std::endl; cout << board.getRows() << " " << board.getCols() << endl;
char currentPlayer = player1->getName(); // Start with the RandomPlayer char currentPlayer = player1->getName(); // Start with the RandomPlayer
while (true) { while (true) {
int row, col; int row, col;

@ -6,7 +6,6 @@
#include "strategic_player.h" #include "strategic_player.h"
class Gameplay { class Gameplay {
private:
Board board; Board board;
Player* player1; // Use pointers to enable polymorphism Player* player1; // Use pointers to enable polymorphism
Player* player2; Player* player2;

7
io.cpp Normal file

@ -0,0 +1,7 @@
#include <iostream>
#include <string>
template<typename T>
void print(T val) {
std::cout << val;
}

@ -5,7 +5,7 @@
using namespace std; using namespace std;
int main(int argc, char* argv[]) { int main() {
int rows, cols; int rows, cols;
char player1Name, player2Name; char player1Name, player2Name;
string player1Type, player2Type; string player1Type, player2Type;

@ -4,13 +4,7 @@
#include "board.h" #include "board.h"
class Player { class Player {
private:
char name;
public: public:
Player(char name){
this->name = name;
}
virtual void selectLineLocation(Board& board, int& row, int& col) = 0; virtual void selectLineLocation(Board& board, int& row, int& col) = 0;
virtual char getName() const = 0; virtual char getName() const = 0;
}; };

@ -1,6 +1,12 @@
#include "random_player.h" #include "random_player.h"
#include <cstdlib> #include <cstdlib>
RandomPlayer::RandomPlayer(char name) {
this->name = name;
srand(time(0)); // Seed the random number generator
}
void RandomPlayer::selectLineLocation(Board& board, int& row, int& col) { void RandomPlayer::selectLineLocation(Board& board, int& row, int& col) {
int rows = board.getRows(); int rows = board.getRows();
int cols = board.getCols(); int cols = board.getCols();
@ -11,3 +17,7 @@ void RandomPlayer::selectLineLocation(Board& board, int& row, int& col) {
col = rand() % (2 * cols - 1); // Random column within the board dimensions col = rand() % (2 * cols - 1); // Random column within the board dimensions
} while (!board.isLineValid(row, col)); // Check if the move is valid } while (!board.isLineValid(row, col)); // Check if the move is valid
} }
char RandomPlayer::getName() const {
return this->name;
}

@ -7,19 +7,14 @@
#include <ctime> #include <ctime>
class RandomPlayer : public Player { class RandomPlayer : public Player {
private:
char name; char name;
public:
RandomPlayer(char name): Player(name) {
srand(static_cast<unsigned int>(time(nullptr)));
this->name = name; public:
} RandomPlayer(char name);
void selectLineLocation(Board &board, int &row, int &col); void selectLineLocation(Board &board, int &row, int &col);
char getName() const override { char getName() const;
return this->name;
}
}; };
#endif //HW4_RANDOM_PLAYER_H #endif //HW4_RANDOM_PLAYER_H

@ -1,19 +1,25 @@
#include "strategic_player.h" #include "strategic_player.h"
using namespace std;
StrategicPlayer::StrategicPlayer(char name) {
this->name = name;
}
void StrategicPlayer::selectLineLocation(Board &board, int &row, int &col) { void StrategicPlayer::selectLineLocation(Board &board, int &row, int &col) {
int rows = board.getRows(); int rows = board.getRows();
int cols = board.getCols(); int cols = board.getCols();
// Step 1: Try to complete a box // Step 1: Try to complete a box
for (int r = 1; r < 2 * rows - 2; r += 2) { // Iterate over box centers (odd rows) for (int r = 1; r < 2 * rows - 2; r += 2) {
for (int c = 1; c < 2 * cols - 2; c += 2) { // Iterate over box centers (odd cols) // Iterate over box centers (odd rows)
for (int c = 1; c < 2 * cols - 2; c += 2) {
// Iterate over box centers (odd cols)
// Check adjacent lines for an opportunity to complete a box // Check adjacent lines for an opportunity to complete a box
if (board.isLineValid(r - 1, c) && // Top line if (board.isLineValid(r - 1, c) && // Top line
board.get(r + 1, c) != ' ' && // Bottom line board.get(r + 1, c) != ' ' && // Bottom line
board.get(r, c - 1) != ' ' && // Left line board.get(r, c - 1) != ' ' && // Left line
board.get(r, c + 1) != ' ') { // Right line board.get(r, c + 1) != ' ') {
// Right line
row = r - 1; row = r - 1;
col = c; col = c;
return; return;
@ -21,7 +27,8 @@ void StrategicPlayer::selectLineLocation(Board& board, int& row, int& col) {
if (board.isLineValid(r + 1, c) && // Bottom line if (board.isLineValid(r + 1, c) && // Bottom line
board.get(r - 1, c) != ' ' && // Top line board.get(r - 1, c) != ' ' && // Top line
board.get(r, c - 1) != ' ' && // Left line board.get(r, c - 1) != ' ' && // Left line
board.get(r, c + 1) != ' ') { // Right line board.get(r, c + 1) != ' ') {
// Right line
row = r + 1; row = r + 1;
col = c; col = c;
return; return;
@ -29,7 +36,8 @@ void StrategicPlayer::selectLineLocation(Board& board, int& row, int& col) {
if (board.isLineValid(r, c - 1) && // Left line if (board.isLineValid(r, c - 1) && // Left line
board.get(r - 1, c) != ' ' && // Top line board.get(r - 1, c) != ' ' && // Top line
board.get(r + 1, c) != ' ' && // Bottom line board.get(r + 1, c) != ' ' && // Bottom line
board.get(r, c + 1) != ' ') { // Right line board.get(r, c + 1) != ' ') {
// Right line
row = r; row = r;
col = c - 1; col = c - 1;
return; return;
@ -37,7 +45,8 @@ void StrategicPlayer::selectLineLocation(Board& board, int& row, int& col) {
if (board.isLineValid(r, c + 1) && // Right line if (board.isLineValid(r, c + 1) && // Right line
board.get(r - 1, c) != ' ' && // Top line board.get(r - 1, c) != ' ' && // Top line
board.get(r + 1, c) != ' ' && // Bottom line board.get(r + 1, c) != ' ' && // Bottom line
board.get(r, c - 1) != ' ') { // Left line board.get(r, c - 1) != ' ') {
// Left line
row = r; row = r;
col = c + 1; col = c + 1;
return; return;
@ -46,15 +55,18 @@ void StrategicPlayer::selectLineLocation(Board& board, int& row, int& col) {
} }
// Step 2: Avoid moves that leave a box with one line remaining // Step 2: Avoid moves that leave a box with one line remaining
for (int r = 0; r < 2 * rows - 1; ++r) { // Iterate over all valid rows for (int r = 0; r < 2 * rows - 1; ++r) {
for (int c = 0; c < 2 * cols - 1; ++c) { // Iterate over all valid cols // Iterate over all valid rows
for (int c = 0; c < 2 * cols - 1; ++c) {
// Iterate over all valid cols
if (board.isLineValid(r, c)) { if (board.isLineValid(r, c)) {
// Simulate placing the line // Simulate placing the line
board.placeLine(r, c, name); board.placeLine(r, c, name);
// Check if this move leaves a box with only one line remaining // Check if this move leaves a box with only one line remaining
bool createsOpportunity = false; bool createsOpportunity = false;
for (int nr = 1; nr < 2 * rows - 2; nr += 2) { // Iterate over box centers for (int nr = 1; nr < 2 * rows - 2; nr += 2) {
// Iterate over box centers
for (int nc = 1; nc < 2 * cols - 2; nc += 2) { for (int nc = 1; nc < 2 * cols - 2; nc += 2) {
if (board.get(nr, nc) == ' ') { if (board.get(nr, nc) == ' ') {
int adjacentLines = 0; int adjacentLines = 0;
@ -63,7 +75,8 @@ void StrategicPlayer::selectLineLocation(Board& board, int& row, int& col) {
if (nc > 0 && board.get(nr, nc - 1) != ' ') adjacentLines++; // Left line if (nc > 0 && board.get(nr, nc - 1) != ' ') adjacentLines++; // Left line
if (nc < 2 * cols - 2 && board.get(nr, nc + 1) != ' ') adjacentLines++; // Right line if (nc < 2 * cols - 2 && board.get(nr, nc + 1) != ' ') adjacentLines++; // Right line
if (adjacentLines == 3) { // Opponent can complete this box if (adjacentLines == 3) {
// Opponent can complete this box
createsOpportunity = true; createsOpportunity = true;
break; break;
} }
@ -94,3 +107,7 @@ void StrategicPlayer::selectLineLocation(Board& board, int& row, int& col) {
} }
} }
} }
char StrategicPlayer::getName() const {
return this->name;
}

@ -9,18 +9,12 @@
#include "player.h" #include "player.h"
class StrategicPlayer: public Player { class StrategicPlayer: public Player {
private:
char name; char name;
public: public:
StrategicPlayer(char name);
StrategicPlayer(char name): Player(name) {
this->name = name;
}
void selectLineLocation(Board& board, int& row, int& col); void selectLineLocation(Board& board, int& row, int& col);
char getName() const override { char getName() const;
return this->name;
}
}; };
#endif //HW4_STRATEGIC_PLAYER_H #endif //HW4_STRATEGIC_PLAYER_H