コード例 #1
0
        int MinValue(CheckerBoard currentBoard, int depth, int alpha, int beta, int currentPlayer)
        {
            if (_nodeGeneration % 10000 == 0 && _nodeGeneration != 0)
            {
                Console.WriteLine("Max Depth: {0}", _maxDepth);
                Console.WriteLine("# of Pruning in Max: {0}", _maxPruning);
                Console.WriteLine("# of Pruning in Min: {0}", _minPruning);
                Console.WriteLine("# of Node Generated: {0}", _nodeGeneration);
                Console.WriteLine("Time Elapsed: {0}", TimeElapsed);
            }
            CheckerStatus status = currentBoard.GetStatus(_currentTurn);

            if (status != CheckerStatus.Continue)
            {
                return((int)status);
            }

            _maxDepth = Math.Max(_maxDepth, depth);
            if (depth == Difficulty)
            {
                return(currentBoard.EvaluateBoard(_currentTurn));
            }
            int v = 999;

            //For each movable piece
            for (var i = 0; i < currentBoard.MovablePieces[currentPlayer].Count(); i++)
            {
                //for each possible positions that the piece can go
                for (var j = 0; j < currentBoard.MoveDict[currentBoard.MovablePieces[currentPlayer][i]].Count(); j++)
                {
                    _nodeGeneration++;
                    //For each possible move make a new checkerboard and move it
                    var newCheckerBoard = new CheckerBoard(currentBoard);
                    var selectedPiece   = newCheckerBoard.GetCheckerPiece(currentBoard.MovablePieces[currentPlayer][i].Row, currentBoard.MovablePieces[currentPlayer][i].Col);
                    newCheckerBoard.SelectedPiece = selectedPiece;
                    newCheckerBoard.HandleMove(currentBoard.MoveDict[currentBoard.MovablePieces[currentPlayer][i]][j]);
                    newCheckerBoard.CheckAllAvailableMoves();
                    int nextTurn = newCheckerBoard.AINextTurn(currentPlayer);

                    v = Math.Min(v, MaxValue(newCheckerBoard, depth + 1, alpha, beta, nextTurn));
                    //pruning
                    if (v <= alpha)
                    {
                        _minPruning++;
                        return(v);
                    }

                    if (v < beta)
                    {
                        beta = v;
                        if (currentBoard == _checkerBoard)
                        {
                            _bestMoveSet = currentBoard.MoveDict[currentBoard.MovablePieces[currentPlayer][i]][j];
                            _bestPiece   = currentBoard.MovablePieces[currentPlayer][i];
                        }
                    }
                }
            }
            return(v);
        }
コード例 #2
0
        /*
         * public void CheckAvailableMoves(CheckerPiece piece)
         * {
         *  int row = piece.Row;
         *  int col = piece.Col;
         *  var tempPossibleMoves = new List<CheckerTile>();
         *  CheckerPiece targetPiece;
         *  //Check if there is a jump move
         *  //At most there are four jump moves with a piece in between and a empty piece after
         *  //Check if the tile is valid and has a piece on it and the color is not yours
         *  if (Board.CheckValidTile(row + 1, col - 1))
         *  {
         *      targetPiece = GetCheckerPiece(row + 1, col - 1);
         *      if (targetPiece != null && targetPiece.Color != piece.Color)
         *      {
         *          //Check if there is a empty space after that piece
         *          if (Board.CheckValidTile(row + 2, col - 2) && GetCheckerPiece(row + 2, col - 2) == null)
         *          {
         *              tempPossibleMoves.Add(Board.TileBoard[row + 2, col - 2]);
         *          }
         *      }
         *  }
         *  if (Board.CheckValidTile(row + 1, col + 1))
         *  {
         *      targetPiece = GetCheckerPiece(row + 1, col + 1);
         *      if(targetPiece != null && targetPiece.Color != piece.Color)
         *      {
         *          //Check if there is a empty space after that piece
         *          if (Board.CheckValidTile(row + 2, col + 2) && GetCheckerPiece(row + 2, col + 2) == null)
         *          {
         *              tempPossibleMoves.Add(Board.TileBoard[row + 2, col + 2]);
         *          }
         *      }
         *  }
         *
         *  if (Board.CheckValidTile(row - 1, col - 1))
         *  {
         *      targetPiece = GetCheckerPiece(row - 1, col - 1);
         *      if (targetPiece != null && targetPiece.Color != piece.Color)
         *      {
         *          //Check if there is a empty space after that piece
         *          if (Board.CheckValidTile(row - 2, col - 2) && GetCheckerPiece(Board.TileBoard[row - 2, col - 2]) == null)
         *          {
         *              tempPossibleMoves.Add(Board.TileBoard[row - 2, col - 2]);
         *          }
         *      }
         *  }
         *
         *  if (Board.CheckValidTile(row - 1, col + 1))
         *  {
         *      targetPiece = GetCheckerPiece(row - 1, col + 1);
         *      if (targetPiece != null && targetPiece.Color != piece.Color)
         *      {
         *          //Check if there is a empty space after that piece
         *          if (Board.CheckValidTile(row - 2, col + 2) && GetCheckerPiece(row - 2, col + 2) == null)
         *          {
         *              tempPossibleMoves.Add(Board.TileBoard[row - 2, col + 2]);
         *          }
         *      }
         *  }
         *
         *  //regular move
         *  //Check for regular move if there is no jump moves
         *  if (!tempPossibleMoves.Any())
         *  {
         *      if (!MustJump[piece.Color])
         *      {
         *          //If the current turn is white
         *          if (piece.Color == 0)
         *          {
         *              //At most there are two regular moves left or right diagonal
         *
         *              //Check if the tile is valid and has no piece on it
         *              if (Board.CheckValidTile(row + 1, col - 1) && GetCheckerPiece(row + 1, col - 1) == null)
         *              {
         *                  tempPossibleMoves.Add(Board.TileBoard[row + 1, col - 1]);
         *              }
         *              if (Board.CheckValidTile(row + 1, col + 1) && GetCheckerPiece(row + 1, col + 1) == null)
         *              {
         *                  tempPossibleMoves.Add(Board.TileBoard[row + 1, col + 1]);
         *              }
         *          }
         *          //current turn is black
         *          else
         *          {
         *              //At most there are two regular moves left or right diagonal
         *
         *              //Check if the tile is valid and has no piece on it
         *              if (Board.CheckValidTile(row - 1, col - 1) && GetCheckerPiece(row - 1, col - 1) == null)
         *              {
         *                  tempPossibleMoves.Add(Board.TileBoard[row - 1, col - 1]);
         *              }
         *              if (Board.CheckValidTile(row - 1, col + 1) && GetCheckerPiece(row - 1, col + 1) == null)
         *              {
         *                  tempPossibleMoves.Add(Board.TileBoard[row - 1, col + 1]);
         *              }
         *          }
         *      }
         *  }
         *  //A jump can be made
         *  else
         *  {
         *      //A previous jump was made
         *      if (JumpMade != null)
         *      {
         *          if (JumpMade == piece)
         *          {
         *              MovablePieces[piece.Color].Add(piece);
         *              MustJump[piece.Color] = true;
         *          }
         *      }
         *      //If there was no previous jump made
         *      else
         *      {
         *          //If this is the first jump
         *          if (MustJump[piece.Color] == false)
         *          {
         *              //Clear the movable piece set
         *              MovablePieces[piece.Color].Clear();
         *              MustJump[piece.Color] = true;
         *          }
         *          //if this piece is a jump piece add it
         *          if (MustJump[piece.Color])
         *          {
         *              MovablePieces[piece.Color].Add(piece);
         *          }
         *      }
         *
         *  }
         *  //Add this to the dictionary if there is actual moves
         *  if (tempPossibleMoves.Count != 0)
         *  {
         *      MoveDict[piece] = tempPossibleMoves;
         *      //if there is no jump add it
         *      if (!MustJump[piece.Color])
         *          MovablePieces[piece.Color].Add(piece);
         *  }
         * }
         */
        public void HandleMove(MoveSet moveSet, int timeDelay = 0)
        {
            foreach (var move in moveSet.MoveList)
            {
                if (MustJump[SelectedPiece.Color])
                {
                    //Remove the jumped piece

                    foreach (var piece in AllPieces.Where(piece => piece.Status == CheckerPieceStatus.Alive))
                    {
                        if (piece.Row == (move.Row + SelectedPiece.Row) / 2 &&
                            piece.Col == (move.Col + SelectedPiece.Col) / 2)
                        {
                            piece.Kill(DateTime.Now);
                            //AllPieces.RemoveAt(i);
                            break;
                        }
                    }
                }
                //Change the piece's position;
                SelectedPiece.Row = move.Row;
                SelectedPiece.Col = move.Col;
                if (timeDelay > 0 && move != moveSet.MoveList.Last())
                {
                    Thread.Sleep(timeDelay);
                }
            }
        }
コード例 #3
0
        //Alpha Beta

        void Ai()
        {
            _bestMoveSet    = null;
            _bestPiece      = null;
            _nodeGeneration = 0;
            _maxPruning     = 0;
            _minPruning     = 0;
            _maxDepth       = 0;
            AlphaBetaSearch(_checkerBoard, _currentTurn);
            //If it never found something b/c it was limited in depth
            if (_bestMoveSet == null && _bestPiece == null)
            {
                var randomPiece = Rand.Next(0, _checkerBoard.MovablePieces[_currentTurn].Count - 1);
                var randomMove  = Rand.Next(0, _checkerBoard.MoveDict[_checkerBoard.MovablePieces[_currentTurn][randomPiece]].Count - 1);
                _bestMoveSet = _checkerBoard.MoveDict[_checkerBoard.MovablePieces[_currentTurn][randomPiece]][randomMove];
                _bestPiece   = _checkerBoard.MovablePieces[_currentTurn][randomPiece];
            }
            _checkerBoard.SelectedPiece = _bestPiece;
            if (_bestPiece != null)
            {
                Console.WriteLine("Moving Piece at Row: {0}, Col: {1}", _bestPiece.Row, _bestPiece.Col);
            }
            if (_bestMoveSet != null)
            {
                Console.WriteLine("{0}", _bestMoveSet.MoveList.ToList());
            }
            Console.WriteLine("Max Depth: {0}", _maxDepth);
            Console.WriteLine("# of Pruning in Max: {0}", _maxPruning);
            Console.WriteLine("# of Pruning in Min: {0}", _minPruning);
            Console.WriteLine("# of Nodes Generated: {0}", _nodeGeneration);
            Console.WriteLine("Time Elapsed: {0}", TimeElapsed);

            if (_selectedParticle != null)
            {
                _selectedParticle.status = ParticleStatus.Dead;
                _selectedParticle        = null;
            }
            if (_bestPiece != null)
            {
                _selectedParticle = _particleManager.Spawn(_particleManager.particleSystemInfoDict["fireSmall"], _checkerBoard.GetCenterOfTile(_bestPiece.Row, _bestPiece.Col));
            }

            Thread.Sleep(TimeDelay);
            //Handle the move to that location
            Debug.Assert(_bestMoveSet != null, "bestMove != null");
            _checkerBoard.HandleMove(_bestMoveSet, TimeDelay);



            if (_selectedParticle != null)
            {
                _selectedParticle.status = ParticleStatus.Dead;
                _selectedParticle        = null;
            }
        }
コード例 #4
0
        public List <MoveSet> CheckJumpMove(CheckerBoard currentBoard, CheckerPiece piece)
        {
            var row = piece.Row;
            var col = piece.Col;

            var jumpMoves        = new List <MoveSet>();
            var possibleLocation = new List <Point> {
                new Point(1, -1), new Point(1, 1), new Point(-1, -1), new Point(-1, 1)
            };

            //Goes to each adjacent tile
            foreach (var location in possibleLocation)
            {
                //Get the adjacent piece that will be jumped
                var targetPiece = currentBoard.GetCheckerPiece(row + location.X, col + location.Y);

                //if the piece exists and the color is the opposite color
                if (targetPiece != null && targetPiece.Color != piece.Color)
                {
                    //Check if there is a empty space after that piece and there is no piece at the location
                    if (Board.CheckValidTile(row + 2 * location.X, col + 2 * location.Y) && currentBoard.GetCheckerPiece(row + 2 * location.X, col + 2 * location.Y) == null)
                    {
                        var jump = new MoveSet(row + 2 * location.X, col + 2 * location.Y);

                        //Check continuous jumps
                        //Generate a copy of the board

                        var nextBoard = new CheckerBoard(currentBoard);
                        nextBoard.SelectedPiece         = nextBoard.GetCheckerPiece(piece.Row, piece.Col);
                        nextBoard.MustJump[piece.Color] = true;
                        //Move
                        nextBoard.HandleMove(row + 2 * location.X, col + 2 * location.Y);

                        //Keep checking for jump moves
                        var nextJumps = CheckJumpMove(nextBoard, nextBoard.SelectedPiece);
                        if (nextJumps.Any())
                        {
                            foreach (var nextJump in nextJumps)
                            {
                                var branch = new MoveSet(jump);
                                branch.MoveList.AddRange(nextJump.MoveList);
                                jumpMoves.Add(branch);
                            }
                        }
                        else
                        {
                            jumpMoves.Add(jump);
                        }
                    }
                }
            }
            return(jumpMoves);
        }
コード例 #5
0
        /*
        public void CheckAvailableMoves(CheckerPiece piece)
        {
            int row = piece.Row;
            int col = piece.Col;
            var tempPossibleMoves = new List<CheckerTile>();
            CheckerPiece targetPiece;
            //Check if there is a jump move
            //At most there are four jump moves with a piece in between and a empty piece after
            //Check if the tile is valid and has a piece on it and the color is not yours
            if (Board.CheckValidTile(row + 1, col - 1))
            {
                targetPiece = GetCheckerPiece(row + 1, col - 1);
                if (targetPiece != null && targetPiece.Color != piece.Color)
                {
                    //Check if there is a empty space after that piece
                    if (Board.CheckValidTile(row + 2, col - 2) && GetCheckerPiece(row + 2, col - 2) == null)
                    {
                        tempPossibleMoves.Add(Board.TileBoard[row + 2, col - 2]);
                    }
                }
            }
            if (Board.CheckValidTile(row + 1, col + 1))
            {
                targetPiece = GetCheckerPiece(row + 1, col + 1);
                if(targetPiece != null && targetPiece.Color != piece.Color)
                {
                    //Check if there is a empty space after that piece
                    if (Board.CheckValidTile(row + 2, col + 2) && GetCheckerPiece(row + 2, col + 2) == null)
                    {
                        tempPossibleMoves.Add(Board.TileBoard[row + 2, col + 2]);
                    }
                }
            }

            if (Board.CheckValidTile(row - 1, col - 1))
            {
                targetPiece = GetCheckerPiece(row - 1, col - 1);
                if (targetPiece != null && targetPiece.Color != piece.Color)
                {
                    //Check if there is a empty space after that piece
                    if (Board.CheckValidTile(row - 2, col - 2) && GetCheckerPiece(Board.TileBoard[row - 2, col - 2]) == null)
                    {
                        tempPossibleMoves.Add(Board.TileBoard[row - 2, col - 2]);
                    }
                }
            }

            if (Board.CheckValidTile(row - 1, col + 1))
            {
                targetPiece = GetCheckerPiece(row - 1, col + 1);
                if (targetPiece != null && targetPiece.Color != piece.Color)
                {
                    //Check if there is a empty space after that piece
                    if (Board.CheckValidTile(row - 2, col + 2) && GetCheckerPiece(row - 2, col + 2) == null)
                    {
                        tempPossibleMoves.Add(Board.TileBoard[row - 2, col + 2]);
                    }
                }
            }

            //regular move
            //Check for regular move if there is no jump moves
            if (!tempPossibleMoves.Any())
            {
                if (!MustJump[piece.Color])
                {
                    //If the current turn is white
                    if (piece.Color == 0)
                    {
                        //At most there are two regular moves left or right diagonal

                        //Check if the tile is valid and has no piece on it
                        if (Board.CheckValidTile(row + 1, col - 1) && GetCheckerPiece(row + 1, col - 1) == null)
                        {
                            tempPossibleMoves.Add(Board.TileBoard[row + 1, col - 1]);
                        }
                        if (Board.CheckValidTile(row + 1, col + 1) && GetCheckerPiece(row + 1, col + 1) == null)
                        {
                            tempPossibleMoves.Add(Board.TileBoard[row + 1, col + 1]);
                        }
                    }
                    //current turn is black
                    else
                    {
                        //At most there are two regular moves left or right diagonal

                        //Check if the tile is valid and has no piece on it
                        if (Board.CheckValidTile(row - 1, col - 1) && GetCheckerPiece(row - 1, col - 1) == null)
                        {
                            tempPossibleMoves.Add(Board.TileBoard[row - 1, col - 1]);
                        }
                        if (Board.CheckValidTile(row - 1, col + 1) && GetCheckerPiece(row - 1, col + 1) == null)
                        {
                            tempPossibleMoves.Add(Board.TileBoard[row - 1, col + 1]);
                        }
                    }
                }
            }
            //A jump can be made
            else
            {
                //A previous jump was made
                if (JumpMade != null)
                {
                    if (JumpMade == piece)
                    {
                        MovablePieces[piece.Color].Add(piece);
                        MustJump[piece.Color] = true;
                    }
                }
                //If there was no previous jump made
                else
                {
                    //If this is the first jump
                    if (MustJump[piece.Color] == false)
                    {
                        //Clear the movable piece set
                        MovablePieces[piece.Color].Clear();
                        MustJump[piece.Color] = true;
                    }
                    //if this piece is a jump piece add it
                    if (MustJump[piece.Color])
                    {
                        MovablePieces[piece.Color].Add(piece);
                    }
                }

            }
            //Add this to the dictionary if there is actual moves
            if (tempPossibleMoves.Count != 0)
            {
                MoveDict[piece] = tempPossibleMoves;
                //if there is no jump add it
                if (!MustJump[piece.Color])
                    MovablePieces[piece.Color].Add(piece);
            }
        }
         */
        public void HandleMove(MoveSet moveSet, int timeDelay = 0)
        {
            foreach (var move in moveSet.MoveList)
            {
                if (MustJump[SelectedPiece.Color])
                {
                    //Remove the jumped piece

                    foreach (var piece in AllPieces.Where(piece => piece.Status == CheckerPieceStatus.Alive))
                    {
                        if (piece.Row == (move.Row + SelectedPiece.Row)/2 &&
                            piece.Col == (move.Col + SelectedPiece.Col) / 2)
                        {
                            piece.Kill(DateTime.Now);
                            //AllPieces.RemoveAt(i);
                            break;
                        }
                    }
                }
                //Change the piece's position;
                SelectedPiece.Row = move.Row;
                SelectedPiece.Col = move.Col;
                if(timeDelay > 0 && move != moveSet.MoveList.Last())
                    Thread.Sleep(timeDelay);
            }
        }
コード例 #6
0
        public List<MoveSet> CheckJumpMove(CheckerBoard currentBoard, CheckerPiece piece)
        {
            var row = piece.Row;
            var col = piece.Col;

            var jumpMoves = new List<MoveSet>();
            var possibleLocation = new List<Point>{new Point(1, -1), new Point(1, 1), new Point(-1, -1), new Point(-1, 1)};

            //Goes to each adjacent tile
            foreach(var location in possibleLocation)
            {
                //Get the adjacent piece that will be jumped
                var targetPiece = currentBoard.GetCheckerPiece(row + location.X, col + location.Y);

                //if the piece exists and the color is the opposite color
                if (targetPiece != null && targetPiece.Color != piece.Color)
                {
                    //Check if there is a empty space after that piece and there is no piece at the location
                    if (Board.CheckValidTile(row + 2 * location.X, col + 2 * location.Y) && currentBoard.GetCheckerPiece(row + 2 * location.X, col + 2 * location.Y) == null)
                    {
                        var jump = new MoveSet(row + 2 * location.X, col + 2 * location.Y);

                        //Check continuous jumps
                        //Generate a copy of the board

                        var nextBoard = new CheckerBoard(currentBoard);
                        nextBoard.SelectedPiece = nextBoard.GetCheckerPiece(piece.Row, piece.Col);
                        nextBoard.MustJump[piece.Color] = true;
                        //Move
                        nextBoard.HandleMove(row + 2 * location.X, col + 2 * location.Y);

                        //Keep checking for jump moves
                        var nextJumps = CheckJumpMove(nextBoard, nextBoard.SelectedPiece);
                        if (nextJumps.Any())
                        {
                            foreach (var nextJump in nextJumps)
                            {
                                var branch = new MoveSet(jump);
                                branch.MoveList.AddRange(nextJump.MoveList);
                                jumpMoves.Add(branch);
                            }
                        }
                        else
                        {
                            jumpMoves.Add(jump);
                        }
                    }
                }
            }
            return jumpMoves;
        }
コード例 #7
0
        //Gets the Max Value
        int MaxValue(CheckerBoard currentBoard, int depth, int alpha, int beta, int currentPlayer)
        {
            if (_nodeGeneration % 10000 == 0 && _nodeGeneration != 0)
            {
                Console.WriteLine("Max Depth: {0}", _maxDepth);
                Console.WriteLine("# of Pruning in Max: {0}", _maxPruning);
                Console.WriteLine("# of Pruning in Min: {0}", _minPruning);
                Console.WriteLine("# of Node Generated: {0}", _nodeGeneration);
                Console.WriteLine("Time Elapsed: {0}", TimeElapsed);
            }
            //Checks to see if it is a utility value
            CheckerStatus status = currentBoard.GetStatus(_currentTurn);

            //If it is return the value
            if (status != CheckerStatus.Continue)
            {
                return((int)status);
            }

            _maxDepth = Math.Max(_maxDepth, depth);

            //Depth Limiter
            if (depth == Difficulty)
            {
                return(currentBoard.EvaluateBoard(_currentTurn));
            }
            var v = -999;

            //Iterate through every movable pieces
            for (var i = 0; i < currentBoard.MovablePieces[currentPlayer].Count(); i++)
            {
                //Iterate through every possible move for the selected piece
                for (var j = 0; j < currentBoard.MoveDict[currentBoard.MovablePieces[currentPlayer][i]].Count(); j++)
                {
                    //Increment node counter
                    _nodeGeneration++;
                    //For each possible move make a new checkerboard and move it
                    var newCheckerBoard = new CheckerBoard(currentBoard);

                    //Select the piece that will be moved
                    var selectedPiece = newCheckerBoard.GetCheckerPiece(currentBoard.MovablePieces[currentPlayer][i].Row, currentBoard.MovablePieces[currentPlayer][i].Col);
                    newCheckerBoard.SelectedPiece = selectedPiece;

                    //Move the piece to a piece location
                    newCheckerBoard.HandleMove(currentBoard.MoveDict[currentBoard.MovablePieces[currentPlayer][i]][j]);

                    newCheckerBoard.CheckAllAvailableMoves();

                    var nextTurn = newCheckerBoard.AINextTurn(currentPlayer);

                    v = Math.Max(v, MinValue(newCheckerBoard, depth + 1, alpha, beta, nextTurn));

                    if (v >= beta)
                    {
                        _maxPruning++;
                        return(v);
                    }

                    if (v > alpha)
                    {
                        alpha = v;
                        if (currentBoard == _checkerBoard)
                        {
                            _bestMoveSet = currentBoard.MoveDict[currentBoard.MovablePieces[currentPlayer][i]][j];
                            _bestPiece   = currentBoard.MovablePieces[currentPlayer][i];
                        }
                    }
                }
            }
            return(v);
        }
コード例 #8
0
ファイル: Move.cs プロジェクト: bookbag/ProjectAlphaIota
 public MoveSet(MoveSet other)
 {
     MoveList = new List<Move>(other.MoveList);
 }
コード例 #9
0
        int MinValue(CheckerBoard currentBoard, int depth, int alpha, int beta, int currentPlayer)
        {
            if (_nodeGeneration % 10000 == 0 && _nodeGeneration != 0)
            {
                Console.WriteLine("Max Depth: {0}", _maxDepth);
                Console.WriteLine("# of Pruning in Max: {0}", _maxPruning);
                Console.WriteLine("# of Pruning in Min: {0}", _minPruning);
                Console.WriteLine("# of Node Generated: {0}", _nodeGeneration);
                Console.WriteLine("Time Elapsed: {0}", TimeElapsed);
            }
            CheckerStatus status = currentBoard.GetStatus(_currentTurn);

            if (status != CheckerStatus.Continue)
            {
                return (int) status;
            }

            _maxDepth = Math.Max(_maxDepth, depth);
            if (depth == Difficulty )
                return currentBoard.EvaluateBoard(_currentTurn);
            int v = 999;
            //For each movable piece
            for (var i = 0; i < currentBoard.MovablePieces[currentPlayer].Count(); i++)
            {
                //for each possible positions that the piece can go
                for (var j = 0; j < currentBoard.MoveDict[currentBoard.MovablePieces[currentPlayer][i]].Count(); j++)
                {
                    _nodeGeneration++;
                    //For each possible move make a new checkerboard and move it
                    var newCheckerBoard = new CheckerBoard(currentBoard);
                    var selectedPiece = newCheckerBoard.GetCheckerPiece(currentBoard.MovablePieces[currentPlayer][i].Row, currentBoard.MovablePieces[currentPlayer][i].Col);
                    newCheckerBoard.SelectedPiece = selectedPiece;
                    newCheckerBoard.HandleMove(currentBoard.MoveDict[currentBoard.MovablePieces[currentPlayer][i]][j]);
                    newCheckerBoard.CheckAllAvailableMoves();
                    int nextTurn = newCheckerBoard.AINextTurn(currentPlayer);

                    v = Math.Min(v, MaxValue(newCheckerBoard, depth + 1, alpha, beta, nextTurn));
                    //pruning
                    if (v <= alpha)
                    {
                        _minPruning++;
                        return v;
                    }

                    if (v < beta)
                    {
                        beta = v;
                        if (currentBoard == _checkerBoard)
                        {
                            _bestMoveSet = currentBoard.MoveDict[currentBoard.MovablePieces[currentPlayer][i]][j];
                            _bestPiece = currentBoard.MovablePieces[currentPlayer][i];
                        }
                    }
                }
            }
            return v;
        }
コード例 #10
0
        //Gets the Max Value
        int MaxValue(CheckerBoard currentBoard, int depth, int alpha, int beta, int currentPlayer)
        {
            if (_nodeGeneration % 10000 == 0 && _nodeGeneration !=0)
            {
                Console.WriteLine("Max Depth: {0}", _maxDepth);
                Console.WriteLine("# of Pruning in Max: {0}", _maxPruning);
                Console.WriteLine("# of Pruning in Min: {0}", _minPruning);
                Console.WriteLine("# of Node Generated: {0}", _nodeGeneration);
                Console.WriteLine("Time Elapsed: {0}", TimeElapsed);
            }
            //Checks to see if it is a utility value
            CheckerStatus status = currentBoard.GetStatus(_currentTurn);

            //If it is return the value
            if (status != CheckerStatus.Continue)
            {
                return (int) status;
            }

            _maxDepth = Math.Max(_maxDepth, depth);

            //Depth Limiter
            if (depth == Difficulty )
                return currentBoard.EvaluateBoard(_currentTurn);
            var v = -999;

            //Iterate through every movable pieces
            for (var i = 0; i < currentBoard.MovablePieces[currentPlayer].Count(); i++)
            {
                //Iterate through every possible move for the selected piece
                for (var j = 0; j < currentBoard.MoveDict[currentBoard.MovablePieces[currentPlayer][i]].Count(); j++)
                {
                    //Increment node counter
                    _nodeGeneration++;
                    //For each possible move make a new checkerboard and move it
                    var newCheckerBoard = new CheckerBoard(currentBoard);

                    //Select the piece that will be moved
                    var selectedPiece = newCheckerBoard.GetCheckerPiece(currentBoard.MovablePieces[currentPlayer][i].Row, currentBoard.MovablePieces[currentPlayer][i].Col);
                    newCheckerBoard.SelectedPiece = selectedPiece;

                    //Move the piece to a piece location
                    newCheckerBoard.HandleMove(currentBoard.MoveDict[currentBoard.MovablePieces[currentPlayer][i]][j]);

                    newCheckerBoard.CheckAllAvailableMoves();

                    var nextTurn = newCheckerBoard.AINextTurn(currentPlayer);

                    v = Math.Max(v, MinValue(newCheckerBoard, depth + 1, alpha, beta, nextTurn));

                    if (v >= beta)
                    {
                        _maxPruning++;
                        return v;
                    }

                    if (v > alpha)
                    {
                        alpha = v;
                        if (currentBoard == _checkerBoard)
                        {
                            _bestMoveSet = currentBoard.MoveDict[currentBoard.MovablePieces[currentPlayer][i]][j];
                            _bestPiece = currentBoard.MovablePieces[currentPlayer][i];
                        }
                    }
                }
            }
            return v;
        }
コード例 #11
0
        //Alpha Beta
        void Ai()
        {
            _bestMoveSet = null;
            _bestPiece = null;
            _nodeGeneration = 0;
            _maxPruning = 0;
            _minPruning = 0;
            _maxDepth = 0;
            AlphaBetaSearch(_checkerBoard, _currentTurn);
            //If it never found something b/c it was limited in depth
            if (_bestMoveSet == null && _bestPiece == null){

                var randomPiece = Rand.Next(0, _checkerBoard.MovablePieces[_currentTurn].Count - 1);
                var randomMove = Rand.Next(0, _checkerBoard.MoveDict[_checkerBoard.MovablePieces[_currentTurn][randomPiece]].Count - 1);
                _bestMoveSet = _checkerBoard.MoveDict[_checkerBoard.MovablePieces[_currentTurn][randomPiece]][randomMove];
                _bestPiece = _checkerBoard.MovablePieces[_currentTurn][randomPiece];
            }
            _checkerBoard.SelectedPiece = _bestPiece;
            if (_bestPiece != null)
                Console.WriteLine("Moving Piece at Row: {0}, Col: {1}", _bestPiece.Row, _bestPiece.Col);
            if (_bestMoveSet != null)
                Console.WriteLine("{0}", _bestMoveSet.MoveList.ToList());
            Console.WriteLine("Max Depth: {0}", _maxDepth);
            Console.WriteLine("# of Pruning in Max: {0}", _maxPruning);
            Console.WriteLine("# of Pruning in Min: {0}", _minPruning);
            Console.WriteLine("# of Nodes Generated: {0}", _nodeGeneration);
            Console.WriteLine("Time Elapsed: {0}", TimeElapsed);

            if (_selectedParticle != null)
            {
                _selectedParticle.status = ParticleStatus.Dead;
                _selectedParticle = null;
            }
            if (_bestPiece != null)
                _selectedParticle = _particleManager.Spawn(_particleManager.particleSystemInfoDict["fireSmall"], _checkerBoard.GetCenterOfTile(_bestPiece.Row, _bestPiece.Col));

            Thread.Sleep(TimeDelay);
            //Handle the move to that location
            Debug.Assert(_bestMoveSet != null, "bestMove != null");
            _checkerBoard.HandleMove(_bestMoveSet, TimeDelay);

            if (_selectedParticle != null)
            {
                _selectedParticle.status = ParticleStatus.Dead;
                _selectedParticle = null;
            }
        }
コード例 #12
0
 public MoveSet(MoveSet other)
 {
     MoveList = new List <Move>(other.MoveList);
 }