public IGameState MakeMove(IGameMove gameMove, IGameState gameState) { TicTacToeMove move = (TicTacToeMove)gameMove; TicTacToeState state = (TicTacToeState)gameState; if (move.X < 0 || move.X > 2) { throw new ArgumentOutOfRangeException("X"); } if (move.Y < 0 || move.Y > 2) { throw new ArgumentOutOfRangeException("Y"); } if (move.Symbol != TicTacToeFieldState.Circle && move.Symbol != TicTacToeFieldState.Cross) { throw new ArgumentOutOfRangeException("Symbol"); } if (state.Fields[move.X][move.Y] != TicTacToeFieldState.Empty) { throw new InvalidOperationException(String.Format("Field is not empty {0} {1} {2}", move.X, move.Y, state.Fields[move.X][move.Y])); } TicTacToeState newState = (TicTacToeState)state.Clone(); newState.Fields[move.X][move.Y] = move.Symbol; return(newState); }
private void ValidateTheSameMove(IGameMove move, List<RuleViolation> validationResult) { if (_board[move.Row, move.Column].Move.GetType() != typeof (NoMove)) { validationResult.Add(new TheSameMoveShouldNotBeMadeAgainRuleValidation(move)); } }
private void ValidateGameAlreadyCompleted(IGameMove move, List<RuleViolation> validationResult) { if (_game.IsCompleted) { validationResult.Add(new GameAlreadyCompletedRuleValidation(move)); } }
// current player performs a move public void DoMove(IGameMove move) { TicTacToeGameMove tttMove = new TicTacToeGameMove(move, this); if (move < 0 || move > board.Length || board[move] != 0) { throw new ArgumentException("Wrong Move!"); } _stateChanged = false; board[move] = currentPlayer; no_moves--; _stateChanged = true; if (CheckWinDirections(currentPlayer, tttMove.GetX, tttMove.GetY)) { // there is a winner _winner = currentPlayer; } else if (no_moves == 0) { // otherwise if there are no more moves there is a tie _winner = 0; } this.playerJustMoved = this.currentPlayer; this.currentPlayer = 3 - this.currentPlayer; }
private IGameMove FindBestMoveImpl(IGameState gameState, GamePlayer currentPlayer) { IGameMove[] moves = _gameLogic.GetPossibleMoves(gameState, currentPlayer); if (moves.Length <= 0) { return(null); } Int32[] rates = new Int32[moves.Length]; Action <Int32> checkSingleMove = moveIndex => { IGameMove nextMove = moves[moveIndex]; IGameState newState = _gameLogic.MakeMove(nextMove, gameState); rates[moveIndex] = (Int32)(FindMoveScore(newState, OtherPlayer(currentPlayer), _depth - 1) * FutureDiscount); }; if (_useParallel) { Parallel.For(0, moves.Length, checkSingleMove); } else { for (Int32 q = 0; q < moves.Length; q++) { checkSingleMove(q); } } return(ExtractResult(currentPlayer, moves, rates)); }
static void Main(string[] args) { IGameBoard board = ...; IConsoleView view = ...; //Game Loop while (!board.IsFinished) { //Print Board Console.WriteLine(view.BoardToString(board)); //Print Possible Moves Console.WriteLine("Possible moves:"); IEnumerable <IGameMove> possibleMoves = board.GetPossibleMoves(); Console.WriteLine(string.Join(",", possibleMoves.Select(view.MoveToString))); //Print the current player and input their move. Console.WriteLine("It is {0}’s turn.", view.PlayerToString(board.CurrentPlayer)); Console.WriteLine("Enter a move: "); string input = Console.ReadLine(); // Parse move and check if it's possible/valid IGameMove toApply = view.ParseMove(input); IGameMove foundMove = possibleMoves.FirstOrDefault(toApply.Equals); if (foundMove == null) { Console.WriteLine("Sorry, that move is invalid."); } else { board.ApplyMove(foundMove); } } }
public DepthLimitedUCTTreeNode(IGameMove move, DepthLimitedUCTTreeNode parent, IGameState state, int depth, int maxDepth, IStateBestMoveEstimator stateEstimator, double constant = 1.0) : base(move, parent, state, constant, false) { this.maxDepth = maxDepth; this.depth = depth; this.stateEstimator = stateEstimator; if (depth <= maxDepth) { untriedMoves = state.GetMoves(); } else { untriedMoves = new List <IGameMove>(); if (!state.isTerminal()) { IGameMove estimatedMove = stateEstimator.EstimateMove(state); state.DoMove(estimatedMove); AddChild(estimatedMove, state); } else { ITreeNode node = this; while (node != null) { node.Update(state.GetResult(node.PlayerWhoJustMoved)); node = node.Parent; } } } }
private void RequestMove(GamePlayer player) { BeforeMove(); IGameMove newMove = this.DoMove(player, this); this.moves = this.moves.Add(newMove); AfterMove(); }
public IEnumerable<RuleViolation> Validate(IGameMove move) { var validationResult = new List<RuleViolation>(); ValidateMoveOrder(move, validationResult); ValidateTheSameMove(move, validationResult); ValidateGameAlreadyCompleted(move, validationResult); return validationResult; }
public virtual ITreeNode AddChild(IGameMove move, IGameState state) { UCTTreeNode n = new UCTTreeNode(move, this, state, constant); untriedMoves.Remove(move); childNodes.Add(n); return(n); }
public override ITreeNode AddChild(IGameMove move, IGameState state) { DepthLimitedUCTTreeNode n = new DepthLimitedUCTTreeNode(move, this, state, depth + 1, maxDepth, stateEstimator, constant); untriedMoves.Remove(move); childNodes.Add(n); return(n); }
private static MinimaxBestMove FindBestMove(IGameBoard b, long alpha, long beta, int depthLeft) { if (depthLeft == 0 || b.IsFinished) { return(new MinimaxBestMove() { Weight = b.BoardWeight, Move = null }); } bool isMaximizing; long bestWeight; if (b.CurrentPlayer == 2) { isMaximizing = false; bestWeight = beta; } else { isMaximizing = true; bestWeight = alpha; } IGameMove bestMove = null; var possible_moves = b.GetPossibleMoves(); foreach (var move in possible_moves) { b.ApplyMove(move); var w = FindBestMove(b, alpha, beta, depthLeft - 1).Weight; b.UndoLastMove(); if (isMaximizing == true && w > bestWeight) { bestWeight = w; bestMove = move; //want the maximum alpha = Math.Max(alpha, w); } else if (isMaximizing == false && w < bestWeight) { bestWeight = w; bestMove = move; //want the minimumz beta = Math.Min(beta, w); } if (alpha >= beta) { break; } } return(new MinimaxBestMove() { Weight = bestWeight, Move = bestMove }); }
public TicTacToeGameMove(IGameMove move, IGameState gameState) { this.x = move.move % gameState.size; this.y = move.move / gameState.size; this.move = x * gameState.size + y; //this.x = move.move / gameState.size - (move.move % gameState.size == 0 ? 1 : 0); //this.y = (move.move % gameState.size == 0 ? gameState.size : (gameState.size >= move.move ? move.move : move.move % gameState.size)) - 1; //this.y = this.y < 0 ? 0 : this.y; }
public void ApplyMove(IGameMove move) { TicTacToeMove m = move as TicTacToeMove; SetPosition(m.Position, CurrentPlayer); MoveHistory.Add(m); mPlayer = -mPlayer; mGameOver = GameIsOver(); }
private void ValidateMoveOrder(IGameMove move, List<RuleViolation> validationResult) { IGameMove lastMove = _moves.LastOrDefault(); if (lastMove != null && lastMove.GetType() == move.GetType()) { validationResult.Add(new MoveOrderRuleViolation(move)); } }
public void ApplyMove(IGameMove move) { TicTacToeMove m = move as TicTacToeMove; SetPosition(m.Position, CurrentPlayer); mWeight += mPlayer * mWeights[m.Position.Row, m.Position.Col]; MoveHistory.Add(m); mPlayer = -mPlayer; mGameOver = GameIsOver(); }
public void Make(IGameMove move) { var result = _rules.Validate(move); if (result.Any()) { throw new RuleViolationException(result); } move.Execute(_board); _moves.Add(move); }
private static MinimaxBestMove FindBestMove(IGameBoard board, long alpha, long beta, int depthLeft, bool isMaximizing) { if (depthLeft == 0 || board.IsFinished) { return new MinimaxBestMove() { Weight = board.BoardWeight, Move = null } } ; IGameMove bestMove = null; foreach (var move in board.GetPossibleMoves()) { board.ApplyMove(move); var w = FindBestMove(board, alpha, beta, depthLeft - 1, !isMaximizing); board.UndoLastMove(); if (isMaximizing && w.Weight > alpha) { bestMove = move; alpha = w.Weight; if (beta <= alpha) { return new MinimaxBestMove() { Weight = beta, Move = bestMove } } ; } else if (!isMaximizing && w.Weight < beta) { bestMove = move; beta = w.Weight; if (beta <= alpha) { return new MinimaxBestMove() { Weight = alpha, Move = bestMove } } ; } } return(new MinimaxBestMove() { Weight = isMaximizing ? alpha : beta, Move = bestMove }); } } }
private IGameMove DoMove(GamePlayer player, IGameState state) { IGameMove move = player.DoMove(state); if (this.ValidateMove(state, move)) { return(move); } throw new IllegalMoveException("Illegal move"); }
public Game(IRules rulesProvider, IBoardBuilder boardBuilder, IGameStatistics gameStatistics) { _rulesProvider = rulesProvider; _boardBuilder = boardBuilder; _history = new LinkedList <History>(); _gameStatistics = gameStatistics; UndoMove = new UndoGameMove(this); RedoMove = new RedoGameMove(this); StopMove = new StopGameMove(this); _board = _boardBuilder.Build(); }
private static MinimaxBestMove FindBestMove(IGameBoard b, int depthLeft, bool maximize, int alpha, int beta) { // Implement the minimax algorithm. // Your first attempt will not use alpha-beta pruning. Once that works, // implement the pruning as discussed in the project notes. if (depthLeft == 0 || b.IsFinished) { return(new MinimaxBestMove { Weight = b.Weight, Move = null }); } int bestWeight = maximize ? Int32.MinValue : Int32.MaxValue; IGameMove bestMove = null; foreach (var move in b.GetPossibleMoves()) { b.ApplyMove(move); int weight = FindBestMove(b, depthLeft - 1, !maximize, alpha, beta).Weight; b.UndoLastMove(); if (maximize && weight > alpha) { alpha = weight; } else if (!maximize && weight < beta) { beta = weight; } if (!(alpha < beta)) { return(new MinimaxBestMove { Weight = maximize ? beta : alpha, Move = bestMove }); } if (maximize && weight > bestWeight) { bestWeight = weight; bestMove = move; } else if (!maximize && weight < bestWeight) { bestWeight = weight; bestMove = move; } } return(new MinimaxBestMove { Weight = bestWeight, Move = bestMove }); }
private static MinimaxBestMove FindBestMove(IGameBoard b, long alpha, long beta, int depthLeft, bool isMaximizing) { //long bestWeight; if (depthLeft == 0 || b.IsFinished) { return new MinimaxBestMove { Weight = b.BoardWeight, Move = null } } ; //bestWeight = (b.CurrentPlayer == 1) ? long.MinValue : long.MaxValue; IGameMove bestMove = null; var possibleMoves = b.GetPossibleMoves(); foreach (IGameMove m in possibleMoves) { b.ApplyMove(m); long weight = (FindBestMove(b, alpha, beta, depthLeft - 1, !isMaximizing)).Weight; b.UndoLastMove(); if (isMaximizing && weight > alpha) { alpha = weight; bestMove = m; } else if (!isMaximizing && weight < beta) { beta = weight; bestMove = m; } if (alpha >= beta) { return(new MinimaxBestMove { Weight = (isMaximizing) ? beta : alpha, Move = bestMove }); } } return(new MinimaxBestMove { Weight = (isMaximizing) ? alpha : beta, Move = bestMove }); } }
private static MinimaxBestMove FindBestMove(IGameBoard b, long alpha, long beta, long depthLeft) { if (depthLeft == 0 || b.IsFinished) { return(new MinimaxBestMove { Move = null, Weight = b.BoardWeight }); } var iAlpha = alpha; var iBeta = beta; bool isMaximizing = b.CurrentPlayer == 1; IGameMove bestMove = null; foreach (var move in b.GetPossibleMoves()) { if (!(iAlpha < iBeta)) { return(new MinimaxBestMove { Weight = isMaximizing ? iBeta : iAlpha, Move = bestMove }); } b.ApplyMove(move); var w = FindBestMove(b, iAlpha, iBeta, depthLeft - 1).Weight; b.UndoLastMove(); if (isMaximizing) { if (w > iAlpha) { iAlpha = w; bestMove = move; } } else { if (w < iBeta) { iBeta = w; bestMove = move; } } } return(new MinimaxBestMove { Weight = isMaximizing ? iAlpha : iBeta, Move = bestMove }); }
private Int32 FindMoveScore(IGameState gameState, GamePlayer currentPlayer, Int32 depth) { if (depth <= 0 || _gameLogic.IsFinished(gameState)) { return(_stateEvaluator.Evaluate(gameState, currentPlayer)); } IGameMove[] moves = _gameLogic.GetPossibleMoves(gameState, currentPlayer); if (moves.Length <= 0) { //// there are no more possible moves to analyse, so return current state evaluation return(_stateEvaluator.Evaluate(gameState, currentPlayer)); } Int32[] rates = new Int32[moves.Length]; Action <Int32> checkSingleMove = moveIndex => { IGameMove nextMove = moves[moveIndex]; IGameState newState = _gameLogic.MakeMove(nextMove, gameState); rates[moveIndex] = (Int32)(FindMoveScore(newState, OtherPlayer(currentPlayer), depth - 1) * FutureDiscount); }; if (_useParallel) { Parallel.For(0, moves.Length, checkSingleMove); } else { for (Int32 q = 0; q < moves.Length; q++) { checkSingleMove(q); } } if (currentPlayer == GamePlayer.PlayerMax) { return(rates.FindFirstMax().Item2); } else if (currentPlayer == GamePlayer.PlayerMin) { return(rates.FindFirstMin().Item2); } else { throw new NotSupportedException(currentPlayer.ToString()); } }
string IConsoleView.MoveToString(IGameMove move) { OthelloMove?casted = move as OthelloMove; if (casted != null) { return(MoveToString(casted)); } else { throw new ArgumentException($"Parameter {nameof(move)} must be of type {nameof(OthelloMove)}"); } }
void IGameBoard.ApplyMove(IGameMove move) { OthelloMove?casted = move as OthelloMove; if (casted != null) { ApplyMove(casted); } else { throw new ArgumentException($"Parameter {nameof(move)} must be of type {nameof(OthelloMove)}"); } }
protected override bool MakeMove(IPlayer player, IGameBoard board, IGameMove move) { if (!this.IsMoveValid(board, move.LaneIndex, move.Die.Value, player.Name)) return false; var targetLane = board.Lanes[move.LaneIndex + move.Die.Value]; if (targetLane.Count == 1 && targetLane[0].Player != player.Name) { targetLane.MovePiece(board.Bar); } move.Lane.MovePiece(targetLane); return true; }
//private static MinimaxBestMove FindBestMove(IGameBoard b, int alpha, int beta, int depthLeft, bool maximize) { //private static Tuple<long, IGameMove> FindBestMove(IGameBoard board, int depth, bool isMaximizing, int alpha, int beta) // alpha = MAXIMUM Lower bound of possible solutions // beta = MINIMUM upper bound of possible solutions //private static MinimaxBestMove FindBestMove(IGameBoard board, int depth, bool isMaximizing, int alpha, int beta) //{ // if (depth == 0 | board.IsFinished) // return new MinimaxBestMove { // Weight = (int)board.BoardWeight, // Move = null // }; // long bestWeight = (isMaximizing) ? Int64.MinValue : Int64.MaxValue; // IGameMove bestMove = null; // foreach (var possibleMove in board.GetPossibleMoves()) { // board.ApplyMove(possibleMove); // var nextBestMove = FindBestMove(board, depth - 1, !isMaximizing, alpha, beta); // board.UndoLastMove(); // // If maximizing the AI's own advantage // if (isMaximizing) { // // if found the nextMove's weight to be higher than the last found (beta) // // replace it with that. // if (nextBestMove.Weight >= beta) { // bestWeight = nextBestMove.Weight; // bestMove = possibleMove; // } // // if the weight is less than alpha, keep searching // if (nextBestMove.Weight <= alpha) continue; // bestMove = possibleMove; // alpha = nextBestMove.Weight; // } // else { // Minimizing the enemy "human"'s advantage // // if human player's weight for that square is less than or equal to // // "alpha" or a calculated/pulled weight or the lowest advantage possible // if (nextBestMove.Weight <= alpha) { // // return that value. // bestWeight = nextBestMove.Weight; // bestMove = possibleMove; // } // // else keep going down the tree // if (nextBestMove.Weight >= beta) continue; // bestMove = possibleMove; // beta = nextBestMove.Weight; // } // } // // when done, this is the result. // return new MinimaxBestMove { // Weight = (int)bestWeight, // Move = bestMove // }; //} // -- Old AI, non alpha/beta -- // private static MinimaxBestMove FindBestMove(IGameBoard board, int depth, bool isMaximizing, int alpha, int beta) { // if (depth == 0 || board.IsFinished) // return new MinimaxBestMove { // Weight = board.BoardWeight, // Move = null // }; // long bestWeight = (isMaximizing) ? Int64.MinValue : Int64.MaxValue; // IGameMove bestMove = null; // foreach (IGameMove possMove in board.GetPossibleMoves()) { // board.ApplyMove(possMove); // MinimaxBestMove w = FindBestMove(board, depth - 1, !isMaximizing, alpha, beta); // board.UndoLastMove(); // // if maximized and weight is greater than best weight // // or not maximized and weight is less than best weight // if (isMaximizing && w.Weight > bestWeight || !isMaximizing && w.Weight < bestWeight) { // bestWeight = w.Weight; // bestMove = possMove; // } // } // return new MinimaxBestMove { // Weight = bestWeight, // Move = bestMove // }; // } private static MinimaxBestMove FindBestMove(IGameBoard board, int depth, bool isMaximizing, long alpha, long beta) { if (depth == 0 || board.IsFinished) { return new MinimaxBestMove { Weight = board.BoardWeight, Move = null } } ; long bestWeight = (isMaximizing) ? Int64.MinValue : Int64.MaxValue; IGameMove bestMove = null; foreach (var move in board.GetPossibleMoves()) { board.ApplyMove(move); var w = FindBestMove(board, depth - 1, !isMaximizing, alpha, beta); board.UndoLastMove(); if (isMaximizing && w.Weight > alpha) { alpha = w.Weight; bestMove = move; } else if (!isMaximizing && w.Weight < beta) { beta = w.Weight; bestMove = move; } if (alpha >= beta) { long opponentsWeight = (isMaximizing) ? beta : alpha; return(new MinimaxBestMove() { Move = move, Weight = opponentsWeight }); } } long myWeight = (isMaximizing) ? alpha : beta; return(new MinimaxBestMove() { Move = bestMove, Weight = myWeight }); } }
public UCTTreeNode(IGameMove move, UCTTreeNode parent, IGameState state, double constant = 1.0, bool generateUntriedMoves = true) { this.move = move; this.parent = parent; this.constant = constant; childNodes = new List <UCTTreeNode>(); wins = 0; visits = 0; playerWhoJustMoved = state.playerJustMoved; if (generateUntriedMoves) { untriedMoves = state.GetMoves(); } }
private static void PlayFourInARowTest() { //String[] input = new[] // { // "oo.o...", // "x......", // "x......", // ".......", // ".......", // ".......", // }; //String[] input = new[] // { // "oooxooo", // "xxxoxxx", // "oooxooo", // "xxxoxxx", // "xoxoxox", // "oo.o...", // }; String[] input = new[] { "oooxooo", "xxxoxxx", "oooxooo", "xxxoxxx", "xoxoxox", "oo.o...", }; FourInARowState state = FourInARowTests.PrepareState(input); FourInARowFactory factory = new FourInARowFactory(); IGameLogic logic = factory.CreateLogic(); MiniMaxAlgorithmImproved alg = new MiniMaxAlgorithmImproved(3, factory, true); PrintState((FourInARowState)state); Int32 res = factory.CreateStateEvaluator().Evaluate(state, GamePlayer.PlayerMax); IGameMove move = alg.FindBestMove(state, GamePlayer.PlayerMax); IGameState newState = logic.MakeMove(move, state); PrintState((FourInARowState)newState); }
//private static MinimaxBestMove FindBestMove(IGameBoard b, int depthLeft, bool maximize) { private static MinimaxBestMove FindBestMove(IGameBoard b, int depthLeft, bool maximize, int alpha, int beta) { // Implement the minimax algorithm. // Your first attempt will not use alpha-beta pruning. Once that works, // implement the pruning as discussed in the project notes. // maximize = player 1 // !maximize = player 2 if (depthLeft == 0 || b.IsFinished) { return(new MinimaxBestMove() { Weight = b.Weight, Move = null }); } //int bestWeight = maximize ? int.MinValue : int.MaxValue; IGameMove bestMove = null; foreach (var m in b.GetPossibleMoves()) { b.ApplyMove(m); MinimaxBestMove w = FindBestMove(b, depthLeft - 1, !maximize, alpha, beta); b.UndoLastMove(); if (maximize && w.Weight > alpha) { alpha = w.Weight; bestMove = m; } else if (!maximize && w.Weight < beta) { beta = w.Weight; bestMove = m; } if (alpha >= beta) { break; } } return(new MinimaxBestMove() { Weight = maximize ? alpha : beta, Move = bestMove }); }
public void GameMoveFactoryTest() { // Arrange IGameMove expectedMove = new TicTacToeMove(TicTacToePlayer.O, new TicTacToeCell(0, 0)); string serializedMove = JsonConvert.SerializeObject(expectedMove); Factory factory = new Factory(); // Act IGameMove result = factory.GameMoveFactory("TicTacToe", serializedMove); // Assert Assert.AreEqual(typeof(TicTacToeMove), result.GetType()); Assert.AreEqual(JsonConvert.SerializeObject(expectedMove), JsonConvert.SerializeObject(result)); }
public GameResult Play(IGameMove player, IGameMove opponent) { if (PlayerWins(player, opponent)) { return(GameResult.Win); } if (PlayerDraws(player, opponent)) { return(GameResult.Draw); } return(GameResult.Loose); }
private static void PlayTicTacToe() { TicTacToeFactory factory = new TicTacToeFactory(); IGameLogic logic = factory.CreateLogic(); MiniMaxAlgorithm alg = new MiniMaxAlgorithm(5, factory); IGameState state = new TicTacToeState(); while (true) { IGameMove move = alg.FindBestMove(state, GamePlayer.PlayerMax); if (null != move) { state = logic.MakeMove(move, state); } else { break; } PrintState((TicTacToeState)state); if (logic.IsFinished(state)) { break; } Int32 x = Int32.Parse(Console.ReadLine()); Int32 y = Int32.Parse(Console.ReadLine()); state = logic.MakeMove(new TicTacToeMove { X = x, Y = y, Symbol = TicTacToeFieldState.Circle }, state); if (logic.IsFinished(state)) { break; } } PrintState((TicTacToeState)state); }
private static void PlayFourInARow() { Console.BufferHeight = 8000; FourInARowFactory factory = new FourInARowFactory(); IGameLogic logic = factory.CreateLogic(); IGameAlgorithm alg = new MiniMaxWithAlfaBetaPrunningDynamic(3, factory); /// new MiniMaxWithAlfaBetaPrunningB(8, factory); // new MiniMaxAlgorithmImproved(6, factory, true); IGameState state = new FourInARowState(); while (true) { IGameMove move = alg.FindBestMove(state, GamePlayer.PlayerMax); if (null != move) { state = logic.MakeMove(move, state); } else { break; } PrintState((FourInARowState)state); if (logic.IsFinished(state)) { break; } Int32 x = Int32.Parse(Console.ReadLine()); state = logic.MakeMove(new FourInARowMove { Column = x, State = FourInARowFieldState.Circle }, state); if (logic.IsFinished(state)) { break; } } PrintState((FourInARowState)state); }
private static MinimaxBestMove FindBestMove(IGameBoard b, long alpha, long beta, int depthLeft) { if (depthLeft == 0 || b.IsFinished) { return(new MinimaxBestMove() { Move = null, Weight = b.BoardWeight }); } bool isMaximizing = (b.CurrentPlayer == 1) ? true : false; //long bestWeight = (isMaximizing) ? long.MinValue : long.MaxValue; IGameMove bestMove = null; foreach (var move in b.GetPossibleMoves()) { b.ApplyMove(move); var w = FindBestMove(b, alpha, beta, depthLeft - 1); b.UndoLastMove(); if (isMaximizing && w.Weight > alpha) { alpha = w.Weight; bestMove = move; } else if (!isMaximizing && w.Weight < beta) { beta = w.Weight; bestMove = move; } if (alpha >= beta) { long opponentsWeight = (isMaximizing) ? beta : alpha; return(new MinimaxBestMove() { Move = move, Weight = opponentsWeight }); } } long myWeight = (isMaximizing) ? alpha : beta; return(new MinimaxBestMove() { Move = bestMove, Weight = myWeight }); }
protected override bool MakeMove(IPlayer player, IGameBoard board, IGameMove move) { if (move.Lane != board.Bar || !this.IsMoveValid(board, move.Die.Value, player.Name)) return false; var lane = move.Lane; var pieceIndex = lane.Count - 1; while (lane[pieceIndex].Player != player.Name) pieceIndex--; var piece = lane[pieceIndex]; lane.RemoveAt(pieceIndex); var targetLane = board.Lanes[move.Die.Value - 1]; if (targetLane.Count == 1 && targetLane[0].Player != player.Name) { targetLane.MovePiece(lane); } targetLane.Add(piece); return true; }
public void Accept(IGameMove move) { AcceptNewMove(move); }
public GameAlreadyCompletedRuleValidation(IGameMove move) { _move = move; }
public void Accept(IGameMove move) { }
protected abstract bool MakeMove(IPlayer player, IGameBoard board, IGameMove move);
public void MovePiece(IPlayer player, IGameBoard board, IGameMove move) { for (var strategy = this; strategy != null && !strategy.MakeMove(player, board, move); strategy = strategy.next) { } }
public MoveOrderRuleViolation(IGameMove move) { _move = move; }
protected override bool MakeMove(IPlayer player, IGameBoard board, IGameMove move) { move.Lane.MovePiece(board.BearedOff); return true; }
public TheSameMoveShouldNotBeMadeAgainRuleValidation(IGameMove move) { _move = move; }