Esempio n. 1
0
        static void EnumUnstackMoves(IList <IMove> dest, GameState state,
                                     PickupAndPlaceMove template, int start, BoardPosition pos, int dir)
        {
            var targetPos = Direction.Offset(pos, dir);

            if (!state.IsPositionLegal(targetPos))
            {
                return;
            }
            var stack = state.Board[targetPos.X, targetPos.Y];

            var  stacktop = state[targetPos];
            bool flatten  = false;

            if (stacktop.HasValue)
            {
                var topstone = Piece.GetStone(stacktop.Value);

                // destination stack must not have cap stone
                if (topstone == Piece.Stone_Cap)
                {
                    return;
                }

                // only capstone by itself may flatten standing stone
                if (topstone == Piece.Stone_Standing)
                {
                    if (template.PickUpMove.PickUpCount - start != 1)
                    {
                        return;
                    }
                    if (!template.PickUpMove.IsCapStone(start))
                    {
                        return;
                    }
                    flatten = true;
                }
            }
            var pickupMove = template.PickUpMove;
            int maxPlace   = pickupMove.PickUpCount - start;

            for (int i = 1; i <= maxPlace; i++)
            {
                for (int j = 0; j < i; j++)
                {
                    template.AddToChain(pickupMove.GeneratePlaceFromStack(j + start, targetPos, flatten));
                }
                if (i + start == pickupMove.PickUpCount)
                {
                    dest.Add(template.ShallowCopy());
                }
                else
                {
                    EnumUnstackMoves(dest, state, template, start + i, targetPos, dir);
                }
                template.RemoveFromEnd(i);
            }
        }
Esempio n. 2
0
        /// <summary>
        /// Enumerate all legal moves in the current board position
        /// </summary>
        /// <param name="dest">Destination list into which moves will be added</param>
        /// <param name="game">Current game state</param>
        /// <param name="moveOrder">Order in which board positions will be considered</param>
        public static void EnumerateMoves(IList <IMove> dest, GameState game, IList <BoardPosition> moveOrder)
        {
            int player = game.Ply & 1;

            if (game.Ply < 2)
            {
                // place enemy flat stone on empty squares
                player = player ^ 1;
                foreach (var pos in moveOrder)
                {
                    if (!game[pos].HasValue)
                    {
                        dest.Add(new PlacePieceMove(Piece.MakePieceID(Piece.Stone_Flat, player), pos, true, false));
                    }
                }
            }
            else
            {
                // place stones on empty squares
                var sremain = game.StonesRemaining[player];
                var cremain = game.CapRemaining[player];
                foreach (var pos in moveOrder)
                {
                    if (!game[pos].HasValue)
                    {
                        if (sremain > 0)
                        {
                            dest.Add(new PlacePieceMove(Piece.MakePieceID(Piece.Stone_Flat, player), pos, true, false));
                            dest.Add(new PlacePieceMove(Piece.MakePieceID(Piece.Stone_Standing, player), pos, true, false));
                        }
                        if (cremain > 0)
                        {
                            dest.Add(new PlacePieceMove(Piece.MakePieceID(Piece.Stone_Cap, player), pos, true, false));
                        }
                    }
                }

                // Move stacks
                foreach (var pos in moveOrder)
                {
                    var stack = game.Board[pos.X, pos.Y];
                    if (stack.Count == 0)
                    {
                        continue;
                    }
                    var topPiece = stack[stack.Count - 1];
                    var topStone = Piece.GetStone(topPiece);
                    if (Piece.GetPlayerID(topPiece) != player)
                    {
                        continue;
                    }

                    for (int pickupCount = 1; pickupCount <= Math.Min(stack.Count, game.Size); pickupCount++)
                    {
                        var pickupMove = new PickUpMove(pos, pickupCount, game);
                        var template   = new PickupAndPlaceMove(pickupMove);
                        for (int dir = 0; dir < 4; dir++)
                        {
                            EnumUnstackMoves(dest, game, template, 0, pos, dir);
                        }
                    }
                }
            }
        }
Esempio n. 3
0
 /// <summary>
 /// Creates a shallow copy by copying the contained moves into a new list
 /// </summary>
 private PickupAndPlaceMove(PickupAndPlaceMove source)
     : base(source.Moves)
 {
 }