private static int AlphaBeta(Board board, int depth, int alpha, int beta) { bool inCheck = board.IsInCheck(board.WhiteMove); // check for this player if (!inCheck && (depth == 0)) // reached maximum search depth and not in check { return(board.Eval()); } // not yet reached maximum search depth List <Move> moves = board.GetMovesOfSide(board.WhiteMove); if ((moves.Count == 0) && inCheck) // check mate for this player { return(board.WhiteMove ? (Int16.MinValue - depth) : (Int16.MaxValue + depth)); // greater depth means we found mate sooner which is preferable } else if (moves.Count == 0) // stalemate { return(board.WhiteMove ? -5: 5); // stalemate is only good if the side to move is currently losing } else if (depth == 0) // reached maximum search depth and IS in check { return(board.WhiteMove ? (board.Eval() - 50) : (board.Eval() + 50)); // being in check is generall a bad thing for the side to move } for (int i = 0, moveCount = moves.Count; i < moveCount; i++) { int currBoardEval; if (board.WhiteMove) // max node { currBoardEval = AlphaBeta(board.Move(moves[i]), depth - 1, alpha, beta); if (currBoardEval > alpha) { alpha = currBoardEval; } } else // min node { currBoardEval = AlphaBeta(board.Move(moves[i]), depth - 1, alpha, beta); if (currBoardEval < beta) { beta = currBoardEval; } } if (alpha >= beta) // prune { break; } } return(board.WhiteMove ? alpha : beta); }
public virtual List <Move> GetMoves(Board board) { List <Move> moves = new List <Move>(); foreach (Square to in this.GetAttacks(board)) { Move potentialMove = new Move(this.Position, to); Board newBoard = board.Move(potentialMove); if (!newBoard.IsInCheck(this.White)) { moves.Add(potentialMove); } } return(moves); }