Checking the winner at TicTacToe?

What would be the best way to see (in a 2-game) Tic Tac Toe game who won? Right now I'm using something similar to the following:

if (btnOne.Text == "X" && btnTwo.Text == "X" && btnThree.Text == "X") { MessageBox.Show("X has won!", "X won!"); return; } else // I'm not going to write the rest but it really just a bunch // if statements. 

So how do I get rid of multiple if?

+4
source share
3 answers

Something together:

 rowSum == 3 || columnSum == 3 || diagnolSum == 3 

..?

+11
source

If you save your buttons in a multidimensional array, you can write some extension methods to get rows, columns, and diagonals.

 public static class MultiDimensionalArrayExtensions { public static IEnumerable<T> Row<T>(this T[,] array, int row) { var columnLower = array.GetLowerBound(1); var columnUpper = array.GetUpperBound(1); for (int i = columnLower; i <= columnUpper; i++) { yield return array[row, i]; } } public static IEnumerable<T> Column<T>(this T[,] array, int column) { var rowLower = array.GetLowerBound(0); var rowUpper = array.GetUpperBound(0); for (int i = rowLower; i <= rowUpper; i++) { yield return array[i, column]; } } public static IEnumerable<T> Diagonal<T>(this T[,] array, DiagonalDirection direction) { var rowLower = array.GetLowerBound(0); var rowUpper = array.GetUpperBound(0); var columnLower = array.GetLowerBound(1); var columnUpper = array.GetUpperBound(1); for (int row = rowLower, column = columnLower; row <= rowUpper && column <= columnUpper; row++, column++) { int realColumn = column; if (direction == DiagonalDirection.DownLeft) realColumn = columnUpper - columnLower - column; yield return array[row, realColumn]; } } public enum DiagonalDirection { DownRight, DownLeft } } 

And if you use a TableLayoutPanel with three rows and three columns, you can easily program your buttons and store them in the Button[3, 3] array Button[3, 3] .

 Button[,] gameButtons = new Button[3, 3]; for (int row = 0; column <= 3; row++) for (int column = 0; column <= 3; column++) { Button button = new Button(); // button... gameLayoutPanel.Items.Add(button); gameButtons[row, column] = button; } 

And check the winner:

 string player = "X"; Func<Button, bool> playerWin = b => b.Value == player; gameButtons.Row(0).All(playerWin) || // ... gameButtons.Column(0).All(playerWin) || // ... gameButtons.Diagonal(DiagonalDirection.DownRight).All(playerWin) || // ... 
+3
source

Another simple way is to save winning positions in the form of data in an array and use a loop to check all possible winning conditions instead of several ifs statements

 // winnable positions var winnables = new[] { "012", "345", "678", "036", "147", "258", "048", "246" }; // extracted from btnOne Two Three.... var gameState = new[] { "X", "O", "X", "whatever" }; string winner = null; // check each winnable positions foreach (var position in winnables) { var pos1 = int.Parse(position[0].ToString()); var pos2 = int.Parse(position[1].ToString()); var pos3 = int.Parse(position[2].ToString()); if (gameState[pos1] == gameState[pos2] && gameState[pos2] == gameState[pos3]) winner = gameState[pos1]; } // do we have a winner? if (!string.IsNullOrEmpty(winner)) /* we've got a winner */ 

In principle, do not use btnOne btnTwo btnThree, use the correct button array or an array that saves the state of the game in a more accessible format, and it will be easier to calculate.

+2
source

All Articles