public void Button_Click(object sender, EventArgs e) { if (this.isThinking) { return; } this.doTurn = new Thread(() => { this.isThinking = true; Cell clickedCell = sender as Cell; if (clickedCell.GetBoard() != null) { if (this.evaluationThread.IsAlive) { this.evaluationThread.Abort(); } this.evaluation.Text = ""; DamkaBoard tmpBoard = clickedCell.GetBoard(); this.board.ClearMoves(); this.board.AppendFromDamkaBoard(tmpBoard); Application.DoEvents(); DamkaBoard bestMove = this.search.GetBestMove(this.depth, isBlack, this.board.GetDamkaBoard()); if (bestMove == null) { MessageBox.Show("Red won!"); this.board.Reset(); this.isThinking = false; return; } this.board.AppendFromDamkaBoard(bestMove); switch (bestMove.WhoWins()) { case Winner.Black: MessageBox.Show("Black won!"); this.board.Reset(); break; case Winner.Red: MessageBox.Show("Red won!"); this.board.Reset(); break; case Winner.Draw: MessageBox.Show("Tie"); this.board.Reset(); break; } SetEvaluation(); this.isThinking = false; return; } this.board.ClearMoves(); this.board.ShowMoves(clickedCell, this.isBlack); this.isThinking = false; }); this.doTurn.Start(); }
private int MinMaxWithoutTT(DamkaBoard board, int depth, bool isRed, int alpha = int.MinValue, int beta = int.MaxValue, bool isFirstMove = true, bool doNull = true) { if (depth <= 0 || board.WhoWins() != Winner.NoOne) { if (!board.IsSkipRequired(isRed)) { return(board.Evaluate(isRed)); } } if (depth >= 4 && !isFirstMove && doNull) { int eval = MinMaxWithoutTT(board.MakeNullMove(), depth - 4, !isRed, alpha, beta - 1, isFirstMove, false); if (eval >= beta) { return(beta); } } if (isRed) { int minEval = int.MaxValue; foreach (DamkaBoard tmpBoard in board.GetAllMoves(isRed)) { int eval = MinMaxWithoutTT(tmpBoard, depth - 1, !isRed, alpha, beta, false, doNull); minEval = Math.Min(minEval, eval); beta = Math.Min(beta, eval); if (beta <= alpha) { break; } } return(minEval); } else { int maxEval = int.MinValue; foreach (DamkaBoard tmpBoard in board.GetAllMoves(isRed)) { int eval = MinMaxWithoutTT(tmpBoard, depth - 1, !isRed, alpha, beta, false, doNull); maxEval = Math.Max(maxEval, eval); alpha = Math.Max(alpha, eval); if (beta <= alpha) { break; } } return(maxEval); } }
private int MinMax(DamkaBoard board, int depth, bool isRed, int alpha = int.MinValue, int beta = int.MaxValue, bool isFirstMove = true, bool doNull = true) { if (depth <= 0 || board.WhoWins() != Winner.NoOne) { if (!board.IsSkipRequired(isRed)) { return(board.Evaluate(isRed)); } } if (isRed) { int minEval = int.MaxValue; foreach (DamkaBoard tmpBoard in board.GetAllMoves(isRed)) { int[] results = tTable.Check(tmpBoard, isRed, depth); int eval; if (results[0] != -15 && results[0] != -20) { eval = results[1]; } else { eval = MinMax(tmpBoard, depth - 1, !isRed, alpha, beta, false, doNull); if (depth > 6) { if (results[0] == -20) { tTable.Update(tmpBoard, isRed, depth, eval); } else { tTable.Add(tmpBoard, isRed, depth, eval); } } } minEval = Math.Min(minEval, eval); beta = Math.Min(beta, eval); if (beta <= alpha) { break; } } return(minEval); } else { int maxEval = int.MinValue; foreach (DamkaBoard tmpBoard in board.GetAllMoves(isRed)) { int[] results = tTable.Check(tmpBoard, isRed, depth); int eval; if (results[0] != -15 && results[0] != -20) { eval = results[1]; } else { eval = MinMax(tmpBoard, depth - 1, !isRed, alpha, beta, false, doNull); if (depth > 6) { if (results[0] == -20) { tTable.Update(tmpBoard, isRed, depth, eval); } else { tTable.Add(tmpBoard, isRed, depth, eval); } } } maxEval = Math.Max(maxEval, eval); alpha = Math.Max(alpha, eval); if (beta <= alpha) { break; } } return(maxEval); } }