vectors and arrays - connect 3 game

Pages: 123
Your example is working more like a tic tac toe board

That's right, that's what it is. However all you need to do is adapt the ideas to connect 4, that's of course if it suits what you have in mind.

The adaptation isn't complicated - an adjustment for making a move and then an adjustment for searching for the relevant patterns.
BTW Are you sure it's connect 4 and not connect 3?
sorry yes its connect 3
ok starting to understand. I need something like this so my program checks for previous moves in the column/if there's any space to make a play there.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24

int main(){
int trueWidth = 3; 
int trueLength = 3; 
}
void CheckBelow ( char board[3][3], playerInfo activePlayer, int dropChoice )
{
	int length, turn;
	length = 3;
	turn = 0;

	do 
	{
		if ( board[length][dropChoice] != 'X' && board[length][dropChoice] != 'O' )
		{
			board[length][dropChoice] = activePlayer.playerID;
			turn = 1;
		}
		else
		--length;
	}while (  turn != 1 );


}
Last edited on
can someone please review my code

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
#include <iostream>
 class Board
 {
 private:
     static const int NO_ROWS{3};
     static const int NO_COLS{3};
     char symbol[3]{'*', 'O', 'X'};
     const char TIE = 'T';
     char board[NO_ROWS][NO_COLS];
     int NO_MOVES{0};
     int MAX_NO_MOVES;
     const int MAX_MOVES = NO_COLS * NO_ROWS; //total cells on the board
     
 public:
     Board()
     {
         for(int row = 0; row < NO_ROWS; row++)
         {
             for(int col = 0; col < NO_COLS; col++)
             {
                 board[row][col] = symbol[0];
             }
         }
     };
     
     ~Board(){};
 // displays board
     void display()
     {
         for(int row = 0; row < NO_ROWS; row++)
         {
             for(int col = 0; col < NO_COLS; col++)
             {
                 std::cout << board[row][col] << ' ';
             }
             std::cout << '\n';
         }
     }
 // checks if the move is valid
     bool move(int player, int row, int col)
     {
         if( isValidMove(row,col) )
         {
             board[row][col] = symbol[player];
             NO_MOVES++;
             display();
             
             return true;
         }
         else
         {
             std::cout
             << row << '-' << col << " is not a valid move ... try again\n\n";
             return false;
         }
     }
     bool isValidMove(int row, int col)
     {
         if( board[row][col] == symbol[0])
             return true;
         else
             return false;
     }
 // switches players after every move
     void SwapPlayer(int player)
             {
                 if (player == 1)
                 {
                     player = 2;
                 }

                 else if (player == 2)
                 {
                     player = 1;
                 }
             }
     
 // User's choice to drop piece
     int dropChoice(int b, char player){
         if(b >=0 && b<= 3)
         {
             if(board[0][b] == ' '){
                 int i;
                 for(i = 0;board[i][b] == ' ';i++)
                     if(i == 2
                        ){board[i][b] = player;
                 return i;}
                 i--;
                 board[i][b] =player;
                 return i;

             }
             else{
                 return -1;
             }

         }
         else{
             return -1;
         }

     }
     
 };
 using namespace std;
// assing names and symbol to user
struct playerInfo
{
    char playerName[10];
    char playerID;
};

//char board[3][3] or char board[NO_ROWS][NO_COLS];?

int PlayerDrop( char board[3][3], playerInfo activePlayer );
void CheckBelow ( char board[3][3], playerInfo activePlayer, int dropChoice );
void DisplayBoard ( char board[3][3] );
int checkThree ( char board[3][3], playerInfo activePlayer );
int FullBoard( char board[3][3] );
void PlayerWin ( playerInfo activePlayer );
int restart ( char board[3][3]);



 int main()
 {
     int dropChoice, win, full, again;
     char board[3][3];
     
     cout << "Let's Play Connect 3. Below is the initial game board.\n"
         <<"Select column number 1, 2, 3; along the top; to indicate your move.\n"
         <<"Enter 0 to quit.\n"
         << endl;
         // display #'s on game board
         cout<<"1 2 3\n";
         cout <<"-----\n";
         // displays board
         Board playingBoard;
         playingBoard.display();
         cout<<endl;
     playerInfo playerOne, playerTwo;
        cout << "Player One please enter your name: ";
         cin  >> playerOne.playerName;
         playerOne.playerID = 'X';
         cout << "Player Two please enter your name: ";
         cin  >> playerTwo.playerName;
         playerTwo.playerID = 'O';
     
         cout << "The two player tokens are X and O. " << playerOne.playerName
        << " begins."<< endl;
     
     // receive user input and print board with user input
     // display #'s on game board
     cout<<"1 2 3\n";
     cout <<"-----\n";
     playingBoard.display();
     
     
     do
         {
             dropChoice = PlayerDrop( board, playerOne );
             CheckBelow( board, playerOne, dropChoice );
             DisplayBoard( board );
             win = checkThree( board, playerOne );
             if ( win == 1 )
             {
                 PlayerWin(playerOne);
                 again = restart(board);
                 if (again == 2)
                 {
                     break;
                 }
             }

             dropChoice = PlayerDrop( board, playerTwo );
             CheckBelow( board, playerTwo, dropChoice );
             DisplayBoard( board );
             win = checkThree( board, playerTwo );
             if ( win == 1 )
             {
                 PlayerWin(playerTwo);
                 again = restart(board);
                 if (again == 2)
                 {
                     break;
                 }
             }
             full = FullBoard( board );
             if ( full == 7 )
             {
                 cout << "The board is full, it is a draw!" << endl;
                 again = restart(board);
             }

         }while ( again != 2 );
     
return 0;
}


//=====================

// check win patterns
int checkThree (char board[3][3], playerInfo activePlayer)
{
    char XO;
    int win;
        
    XO = activePlayer.playerID;
    win = 0;

    for( int i = 3; i >= 1; --i )
    {
        
        for( int j = 3; j >= 1; --j )
        {
// decending diagonal
            if( board[i][j] == XO     &&
                board[i-1][j-1] == XO &&
                board[i+1][j+1] == XO )
            {
                win = 1;
            }
// ascending diagonal
            if( board[i][j] == XO     &&
                board[i+1][j-1] == XO &&
                board[i-1][j+1] == XO )
            {
                win = 1;
            }
// top horizontal
            if( board[i-1][j-1] == XO   &&
                board[i-1][j] == XO &&
                board[i-1][j+1] == XO)
            {
                win = 1;
            }
 // middle horizontal
            if( board[i][j] == XO   &&
                board[i][j-1] == XO &&
                board[i][j+1] == XO )
            {
                win = 1;
            }
// bottom horizontal
            if( board[i+1][j-1] == XO     &&
                board[i+1][j] == XO &&
                board[i+1][j+1] == XO)
            {
                win = 1;
            }
//left vertical
            if ( board[i-1][j-1] == XO   &&
                 board[i][j-1] == XO &&
                 board[i+1][j-1] == XO )
            {
                win = 1;
            }
//middle vertical
            if ( board[i-1][j] == XO   &&
                board[i][j] == XO &&
                board[i+1][j] == XO )
            {
                  win = 1;
            }
// right vertival
            if ( board[i-1][j+1] == XO   &&
                board[i][j+1] == XO &&
                board[i+1][j+1] == XO )
            {
                win = 1;
            }
        }
        
    }
    return win;
    }

int fullBoard(char board[3][3])
{
    int full;
    full = 0;
    for ( int i = 1; i <= 3; ++i )
    {
        if ( board[1][i] != '*' )
            ++full;
    }

return full;
}


int restart (char board[3][3])
{
    int restart;

    cout << "Would you like to play again? Yes(1) No(2): ";
    cin  >> restart;
    if ( restart == 1 )
    {
        for(int i = 1; i <= 3; i++)
        {
            for(int j = 1; j <= 3; j++)
            {
                board[i][j] = '*';
            }
        }
    }
    else
// need counted to calculate amount of games played and how many were won/who won the most
        cout << "Goodbye!\n"
        << "Player 1 won: 1 times. 100.00%  Player 2 won: 0 times. 0.00%"
        <<"This ends the Connect game.\n"
        << "Goodbye!\n";

    
    
return restart;
}

// player wins
void PlayerWin ( playerInfo activePlayer )
{
    cout << endl << activePlayer.playerName << " connected three, You Win!" << endl;
}
Last edited on
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
#include <iostream>
#include <vector>

class Board
{
private:
    int NO_ROWS{3};
    int NO_COLS{3};
    
    char symbol[3]{'*', 'O', 'X'};
    std::vector<std::vector<char>> board;
    
    int NO_MOVES{0};
    int MAX_NO_MOVES = NO_ROWS * NO_COLS;
    
    bool game_over{false};
    
public:
    Board(int rows = 3, int cols = 5)
    {
        NO_ROWS = rows;
        NO_COLS = cols;
        initialize();
    };
    
    ~Board(){};
    
    void initialize()
    {
        board.resize(NO_ROWS, std::vector<char>(NO_COLS, symbol[0]));
        
        for(int row = 0; row < NO_ROWS; row++)
        {
            for(int col = 0; col < NO_COLS; col++)
            {
                board[row][col] = symbol[0];
            }
        }
    }
    
    bool isWin(int aPlayer)
    {
        char sym = getSymbol(aPlayer);
        
        for(int row = 0; row < NO_ROWS; row++)
        {
            for( int col = 0; col < NO_COLS; col++)
            {
                // A) VERTICAL - checks out
                if(
                   row - 1 >= 0 && row + 1 < NO_ROWS &&
                   
                   board[row - 1][col] == sym &&
                   board[row][col] == sym &&
                   board[row + 1][col] == sym
                   )
                    return true;
                
                // B) DIAGONAL ( +1:1 slope )
                if
                    (
                     row - 1 >= 0 && col + 1 < NO_COLS &&
                     row + 1 < NO_ROWS && col - 1 >= 0 &&
                     
                     board[row - 1][col + 1] == sym &&
                     board[row][col] == sym &&
                     board[row + 1][col - 1] == sym
                     )
                    return true;
                
                // C) HORIZONTAL
                if(
                   col + 1 < NO_COLS  && col - 1 >= 0 &&
                   
                   board[row][col + 1] == sym &&
                   board[row][col] == sym &&
                   board[row][col - 1] == sym
                   )
                    return true;
                
                // D) DIAGONAL ( -1:1 slope )
                if
                    (
                     row + 1 < NO_ROWS && col + 1 < NO_COLS &&
                     row - 1 >= 0 && col - 1 >= 0 &&
                     
                     board[row + 1][col + 1] == sym &&
                     board[row][col] == sym &&
                     board[row - 1][col - 1] == sym
                     )
                    return true;
            }
        }
        
        return false;
    }
    
    void display()
    {
        for(int row = 0; row < NO_ROWS; row++)
        {
            std::cout << row << ' ' ;
            for(int col = 0; col < NO_COLS; col++)
            {
                std::cout << board[row][col] << ' ';
            }
            std::cout << '\n';
        }
        std::cout << "  ";
        for(int col = 0; col < NO_COLS; col++)
        {
            std::cout << col << ' ';
        }
        std::cout
        << '\n'
        << "No. of moves: " << NO_MOVES << '\n';
    }
    
    void set(int aPlayer, int col)
    {
        for(int row = NO_ROWS - 1; row >= 0; row--)
        {
            if(board[row][col] == symbol[0])
            {
                board[row][col] = symbol[aPlayer];
                return;
            }
        }
    }
    
    bool move(int player, int col)
    {
        if( isValidMove(col) )
        {
            set(player, col);
            NO_MOVES++;
            return true;
        }
        else
        {
            return false;
        }
    }
    
    bool isValidMove(int col)
    {
        if(col < 0 or col >= NO_COLS)
            return false;
        
        if( isFull(col) )
            return false;
        else
            return true;
    }
    
    bool isFull(int col)
    {
        for(int row = 0; row < NO_ROWS; row++)
        {
            if(board[row][col] == symbol[0])
                return false;
        }
        return true;
    }
    
    int getMoveCount()
    {
        return NO_MOVES;
    }
    
    int getMoveCountLimit()
    {
        return MAX_NO_MOVES;
    }
    
    char getSymbol(int aPlayer)
    {
        return symbol[aPlayer];
    }
    
    bool isGameOver()
    {
        return game_over;
    }
    
    void setGameOver()
    {
        game_over = true;
    }
};


int main()
{
    Board bored(3,3);
    
    bool turn{true};
    
    const int player_O{1};
    const int player_X{2};
    
    int current_player{player_O}; // 'O' always starts play
    int row{-99}, col{-99};
    
    bored.display();
    
    std::cout << "->  O to move ... ";
    
    while(
          bored.isGameOver() == false &&
          bored.getMoveCount() < bored.getMoveCountLimit()
          )
    {
        std::cout << "enter col ";
        std::cin >> col;
        
        if( bored.isValidMove(col) )
        {
            std::cout << "Move is valid\n";
            
            bored.move(current_player, col);
            bored.display();
            
            if (bored.isWin(current_player) == true)
            {
                std::cout
                << "Player: " << bored.getSymbol(current_player)
                << " has won\n";
                
                bored.setGameOver();
            }
            else
            {
                turn = !turn;
            }
        }
        else
        {
            std::cout << "Invalid move - TRY AGAIN!\n";
        }
        
        if(turn)
        {
            current_player = player_O;
        }
        else
        {
            current_player = player_X;
        }
        
        std::cout
        << "->  Player " << bored.getSymbol(current_player) << " to move\n";
    }
    
    return 0;
}



0 * * * 
1 * * * 
2 * * * 
  0 1 2 
No. of moves: 0
->  O to move ... enter col 2
Move is valid
0 * * * 
1 * * * 
2 * * O 
  0 1 2 
No. of moves: 1
->  Player X to move
enter col 1
Move is valid
0 * * * 
1 * * * 
2 * X O 
  0 1 2 
No. of moves: 2
->  Player O to move
enter col 1
Move is valid
0 * * * 
1 * O * 
2 * X O 
  0 1 2 
No. of moves: 3
->  Player X to move
enter col 0
Move is valid
0 * * * 
1 * O * 
2 X X O 
  0 1 2 
No. of moves: 4
->  Player O to move
enter col 0
Move is valid
0 * * * 
1 O O * 
2 X X O 
  0 1 2 
No. of moves: 5
->  Player X to move
enter col 2
Move is valid
0 * * * 
1 O O X 
2 X X O 
  0 1 2 
No. of moves: 6
->  Player O to move
enter col 0
Move is valid
0 O * * 
1 O O X 
2 X X O 
  0 1 2 
No. of moves: 7
Player: O has won
->  Player O to move
Program ended with exit code: 0
Last edited on
is there a reason to add the number of moves?
also how can I edit the code so it keeps looping after every game until the user stops playing.

for example,
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
int restart (char board[3][3])
{
    int restart;

    cout << "Would you like to play again? Yes(1) No(2): ";
    cin  >> restart;
    if ( restart == 1 )
    {
        for(int i = 1; i <= 3; i++)
        {
            for(int j = 1; j <= 3; j++)
            {
                board[i][j] = '*';
            }
        }
    }
    else
        cout 
//# games won/# of games * 100 = % of games won
        << "Player 1 won: 1 times. 100.00%  Player 2 won: 0 times. 0.00%"
        <<"This ends the Connect game.\n"
        << "Goodbye!\n";

    


in order to calculate this I also need to take a forfeit as a loss.
I was thinking I could prompt the user like this
(enter col 1-3, zero to quit) or (enter col 0-2, q to quit)
Last edited on
is there a reason to add the number of moves?
Only if you want to know when there are no moves left instead of checking that all columns are full which would be another way of ending a game.

how can I edit the code so it keeps looping after every game until the user stops playing.
Give it a go. I'll leave it to you to work that out - there are tons of examples with a while loop/menu system floating around.

Remember there is an initialize() method in the class. Besides, if all else fails and you are running the risk of not meeting your 2 day deadline, just pin a note on your assignment submission to reboot your PC if anyone wants to play again
Good luck! << "Goodbye\n" :)
this is what I have so far. do I need to do if/else statements here?


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
               if (bored.isWin(current_player) == true)
            {
                std::cout
                << "\nCongratulations! Player: " << bored.getSymbol(current_player)
                << " has won!";
                
                char y,n;
                double winsPlayerOne;
                double winsPlayerTwo;
                int totalPlays;
                
                std::cout
                <<"\nDo you want to play again? (y/n): ";
                //if yes start game over
                if (restart){
                    std::cin << y
                    
                }
                
                //if no bored.setGameOver();
                bored.setGameOver();
                std::cout << "\nPlayer 1 won: " << winsPlayerOne <<" times." << winsPlayerOne/totalPlays*100
                << "Player 2 won: " winsPlayerTwo <<" times." << winsPlayerTwo/totalPlays*100
                <<"\nThis ends the Connect game. Goodbye.";
                
            }
            else
            {
                turn = !turn;
            }
            
Last edited on
do I need to do if/else statements here?
Short answer is 'probably no', or 'could be'.

What you could do to improve is a separate menu interface via a function that controls/manages all aspects of the game incorporating a switch instead of if cascades.

When the game is over (or at the start), for whatever reason - eg a win or draw - then display the menu giving user(s) the ability to choose - eg to continue or quit.
would an enum menu be a better option?

1
2
3
4
5
6
7
8
9
10
                //menu options
                   enum menu { play_again = 'y', dont_play again = 'n', quit = 'q' };

                
                //counters
                   menu menuChoice {};
                   int winsPlayerOne_count {}, winsPlayerTwo_count {}, totalGames_count {};
                
                
                
Last edited on
Appears too complicated to me :(

I'll show you a simple one shortly.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
 
#include <iostream>
#include <iostream>
#include <vector>

class Board
{
private:
    int NO_ROWS{3};
    int NO_COLS{3};
    char symbol[3]{'*', 'O', 'X'};
    std::vector<std::vector<char>> board;
    int NO_MOVES{0};
    bool game_over{false};
    
public:
    Board(int rows = 3, int cols = 5)
    {
        NO_ROWS = rows;
        NO_COLS = cols;
        initialize();
    };
    
    ~Board(){};
    
    void initialize()
    {
        game_over = false ;
        NO_MOVES = 0;
        board.resize(NO_ROWS, std::vector<char>(NO_COLS, symbol[0]));
        
        for(int row = 0; row < NO_ROWS; row++)
        {
            for(int col = 0; col < NO_COLS; col++)
            {
                board[row][col] = symbol[0];
            }
        }
    }
    
    bool isWin(int aPlayer)
    {
        char sym = getSymbol(aPlayer);
        
        for(int row = 0; row < NO_ROWS; row++)
        {
            for( int col = 0; col < NO_COLS; col++)
            {
                // A) VERTICAL
                if(
                   row - 1 >= 0 && row + 1 < NO_ROWS &&
                   
                   board[row - 1][col] == sym &&
                   board[row][col] == sym &&
                   board[row + 1][col] == sym
                   )
                    return true;
                
                // B) DIAGONAL ( +1:1 slope )
                if
                    (
                     row - 1 >= 0 && col + 1 < NO_COLS &&
                     row + 1 < NO_ROWS && col - 1 >= 0 &&
                     
                     board[row - 1][col + 1] == sym &&
                     board[row][col] == sym &&
                     board[row + 1][col - 1] == sym
                     )
                    return true;
                
                // C) HORIZONTAL
                if(
                   col + 1 < NO_COLS  && col - 1 >= 0 &&
                   
                   board[row][col + 1] == sym &&
                   board[row][col] == sym &&
                   board[row][col - 1] == sym
                   )
                    return true;
                
                // D) DIAGONAL ( -1:1 slope )
                if
                    (
                     row + 1 < NO_ROWS && col + 1 < NO_COLS &&
                     row - 1 >= 0 && col - 1 >= 0 &&
                     
                     board[row + 1][col + 1] == sym &&
                     board[row][col] == sym &&
                     board[row - 1][col - 1] == sym
                     )
                    return true;
            }
        }
        
        return false;
    }
    
    void display()
    {
        for(int row = 0; row < NO_ROWS; row++)
        {
            std::cout << row << ' ' ;
            for(int col = 0; col < NO_COLS; col++)
            {
                std::cout << board[row][col] << ' ';
            }
            std::cout << '\n';
        }
        std::cout << "  ";
        for(int col = 0; col < NO_COLS; col++)
        {
            std::cout << col << ' ';
        }
        std::cout
        << '\n'
        << "No. of moves: " << NO_MOVES << '\n';
    }
    
    void set(int aPlayer, int col)
    {
        for(int row = NO_ROWS - 1; row >= 0; row--)
        {
            if(board[row][col] == symbol[0])
            {
                board[row][col] = symbol[aPlayer];
                return;
            }
        }
    }
    
    bool move(int player, int col)
    {
        if( isValidMove(col) )
        {
            set(player, col);
            NO_MOVES++;
            return true;
        }
        else
        {
            return false;
        }
    }
    
    bool isValidMove(int col)
    {
        if(col < 0 or col >= NO_COLS)
            return false;
        
        if( isFull(col) )
            return false;
        else
            return true;
    }
    
    bool isFull(int col)
    {
        for(int row = 0; row < NO_ROWS; row++)
        {
            if(board[row][col] == symbol[0])
                return false;
        }
        return true;
    }
    
    int getMoveCount()
    {
        return NO_MOVES;
    }
    
    int getMoveLimit()
    {
        return NO_ROWS * NO_COLS;
    }
    
    char getSymbol(int aPlayer)
    {
        return symbol[aPlayer];
    }
    
    bool isGameOver()
    {
        return game_over;
    }
    
    void setGameOver()
    {
        game_over = true;
    }
};

char menu()
{
    std::cout
    << "******************\n"
    << "       MENU\n"
    << " 1 - New game\n"
    << " 2 - Something\n"
    << " q - Quit\n"
    << "******************\n"
    << "   Enter choice: ";
    
    char choice;
    std::cin >> choice;
    
    return choice;
}

int main()
{
    Board bored(3,3);
    
    char selection{'?'};
    while( selection != 'Q' )
    {
        selection = toupper( menu() );
        switch(selection)
        {
            case '1':
            {
                
                std::cout << "Option 1 stub\n";
                
                bored.initialize();
                bool turn{true};
                
                const int player_O{1};
                const int player_X{2};
                
                int current_player{player_O}; // 'O' always starts play
                int col{-99};
                
                bored.display();
                
                std::cout << "->  O to move ... ";
                
                while(
                      bored.isGameOver() == false &&
                      bored.getMoveCount() <= bored.getMoveLimit()
                      )
                {
                    std::cout << "enter col ";
                    std::cin >> col;
                    
                    if( bored.isValidMove(col) )
                    {
                        std::cout << "Move is valid\n";
                        
                        bored.move(current_player, col);
                        bored.display();
                        
                        if (bored.isWin(current_player) == true)
                        {
                            std::cout
                            << "Player: " << bored.getSymbol(current_player)
                            << " has won\n";
                            
                            bored.setGameOver();
                        }
                        else
                        {
                            turn = !turn;
                        }
                    }
                    else
                    {
                        std::cout << "Invalid move - TRY AGAIN!\n";
                    }
                    
                    if(turn)
                    {
                        current_player = player_O;
                    }
                    else
                    {
                        current_player = player_X;
                    }
                    
                    std::cout
                    << "->  Player " << bored.getSymbol(current_player) << " to move\n";
                }
            }
                break;
            case '2':
                std::cout << "Option 2 stub\n";
                break;
            case 'Q':
                std::cout << "Goodbye\n";
                break;
            default:
                std::cout << "--->>>> Invalid choice\n";
        }
    }
    return 0;
}
Last edited on
thank you I will implement that.
I'm having trouble figuring out how to calculate total games in order to calculate the percentage of games won by both players
would something like this work?


1
2
3
4
5
int totalGames = 0;
while(waiting for a winner or for quit)
{
    totalGames++; //round counter.  
}
Last edited on
Put the ++calculation inside option '1' - new game to increment a game_counter declared and initialized in main()

im a little bit confused on how to work this out

If a player quits the game early, the game is forfeit, and that player loses that game. After the game, ask the user if he/she wants to continue. Provide percentage of wins for both players.


how do I set up my counters to count a win for the opposing player if the current player quits mid game? should I keep 'quit' as a case or incorporate inside option '1'


I got my counters for the amount of games won and the counter for the amount of games played.
Last edited on
this is the last thing I need some help with

is this a good set up? what should I put inside the parenthesis?
1
2
3
4
5
6
7
if (player X inputs 3 == true)
          { playerOGamesWon++;
             bored.setGameOver(); }

if (player O inputs 3 == true)
          { playerXGamesWon++;
             bored.setGameOver(); }
Last edited on
I’d use -99 instead of 3 because it’s less prone to user error.
Only one if is required because you know who the current_player is and therefore who the other one is.
If the current player abandons the game then the other one is the winner.

All that is very easy for you to write the code yourself.

Abandoning the game is a move option, not a main menu option.
Last edited on
just found an error while testing it
this is what has worked the best but it hasn't worked perfectly because it prints the message when 7 moves have been made. should I make a new identifier in the place of col?

1
2
3
4
5
6
while(
bored.isGameOver() == false &&
bored.getMoveCount() == bored.getMoveLimit()
// am I able to print this message
std::cout <<"The game is a tie";
)

// how do I correctly incorporate
Player O to move: 0
O * *
X O X
O X O
-----
0 1 2
Player: O has won!
The game is a tie!
Last edited on
The game is a draw when all 3 columns are full and there is no win declared.

The maximum number of moves is 9 not 7 which is a leftover from the tic tac toe days. There is no longer any need for the max moves variable.
got it thank you
Pages: 123