示例#1
0
        public double Calculate(Move move)
        {
            if (move.IsEmpty)
            {
                return(Move.RejectScore);
            }

            ScoreInfo score = new ScoreInfo(Coefficients, Group0);

            int from    = move.From;
            int fromRow = move.FromRow;
            int to      = move.To;
            int toRow   = move.ToRow;

            if (move.Type == MoveType.CompositeSinglePile)
            {
                return(CalculateCompositeSinglePileScore(move));
            }
            Pile fromPile = FindTableau[from];
            Pile toPile   = FindTableau[to];

            if (toPile.Count == 0)
            {
                return(CalculateLastResortScore(move));
            }
            bool isSwap       = move.Type == MoveType.Swap;
            Card fromParent   = fromRow != 0 ? fromPile[fromRow - 1] : Card.Empty;
            Card fromChild    = fromPile[fromRow];
            Card toParent     = toRow != 0 ? toPile[toRow - 1] : Card.Empty;
            Card toChild      = toRow != toPile.Count ? toPile[toRow] : Card.Empty;
            int  oldOrderFrom = GetOrder(fromParent, fromChild);
            int  newOrderFrom = GetOrder(toParent, fromChild);
            int  oldOrderTo   = isSwap ? GetOrder(toParent, toChild) : 0;
            int  newOrderTo   = isSwap ? GetOrder(fromParent, toChild) : 0;

            score.Order = newOrderFrom - oldOrderFrom + newOrderTo - oldOrderTo;
            if (score.Order < 0)
            {
                return(Move.RejectScore);
            }
            score.Reversible  = oldOrderFrom != 0 && (!isSwap || oldOrderTo != 0);
            score.Uses        = CountUses(move);
            score.OneRunDelta = !isSwap?RunFinder.GetOneRunDelta(oldOrderFrom, newOrderFrom, move) : 0;

            int faceFrom = (int)fromChild.Face;
            int faceTo   = isSwap ? (int)toChild.Face : 0;

            score.FaceValue = Math.Max(faceFrom, faceTo);
            bool wholePile        = fromRow == 0 && toRow == toPile.Count;
            int  netRunLengthFrom = RunFinder.GetNetRunLength(newOrderFrom, from, fromRow, to, toRow);
            int  netRunLengthTo   = isSwap ? RunFinder.GetNetRunLength(newOrderTo, to, toRow, from, fromRow) : 0;

            score.NetRunLength = netRunLengthFrom + netRunLengthTo;
#if true
            int newRunLengthFrom = RunFinder.GetNewRunLength(newOrderFrom, from, fromRow, to, toRow);
            int newRunLengthTo   = isSwap ? RunFinder.GetNewRunLength(newOrderTo, to, toRow, from, fromRow) : 0;
            score.Discards = newRunLengthFrom == 13 || newRunLengthTo == 13;
#endif
            score.DownCount     = FindTableau.GetDownCount(from);
            score.TurnsOverCard = wholePile && score.DownCount != 0;
            score.CreatesSpace  = wholePile && score.DownCount == 0;
            score.NoSpaces      = FindTableau.NumberOfSpaces == 0;
            if (score.Order == 0 && score.NetRunLength < 0)
            {
                return(Move.RejectScore);
            }
            int delta = 0;
            if (score.Order == 0 && score.NetRunLength == 0)
            {
                if (!isSwap && oldOrderFrom == 1 && newOrderFrom == 1)
                {
                    delta = RunFinder.GetRunDelta(from, fromRow, to, toRow);
                }
                if (delta <= 0)
                {
                    return(Move.RejectScore);
                }
            }
            score.IsCompositeSinglePile = false;

            return(score.Score);
        }
示例#2
0
        public bool IsViable(Move move)
        {
            int from    = move.From;
            int fromRow = move.FromRow;
            int to      = move.To;
            int toRow   = move.ToRow;

            Pile fromPile = FindTableau[from];
            Pile toPile   = FindTableau[to];

            if (toPile.Count == 0)
            {
                if (fromPile.Count == 0 && FindTableau.GetDownCount(from) == 0)
                {
                    return(false);
                }
                else if (fromRow != 0 && fromPile[fromRow - 1].IsTargetFor(fromPile[fromRow]))
                {
                    return(false);
                }
                return(true);
            }
            bool isSwap       = move.Type == MoveType.Swap;
            Card fromParent   = fromRow != 0 ? fromPile[fromRow - 1] : Card.Empty;
            Card fromChild    = fromPile[fromRow];
            Card toParent     = toRow != 0 ? toPile[toRow - 1] : Card.Empty;
            Card toChild      = toRow != toPile.Count ? toPile[toRow] : Card.Empty;
            int  oldOrderFrom = GetOrder(fromParent, fromChild);
            int  newOrderFrom = GetOrder(toParent, fromChild);
            int  oldOrderTo   = isSwap ? GetOrder(toParent, toChild) : 0;
            int  newOrderTo   = isSwap ? GetOrder(fromParent, toChild) : 0;
            int  order        = newOrderFrom - oldOrderFrom + newOrderTo - oldOrderTo;

            if (order < 0)
            {
                return(false);
            }
            int netRunLengthFrom = RunFinder.GetNetRunLength(newOrderFrom, from, fromRow, to, toRow);
            int netRunLengthTo   = isSwap ? RunFinder.GetNetRunLength(newOrderTo, to, toRow, from, fromRow) : 0;
            int netRunLength     = netRunLengthFrom + netRunLengthTo;

            if (order == 0 && netRunLength < 0)
            {
                return(false);
            }
            int delta = 0;

            if (order == 0 && netRunLength == 0)
            {
                if (!isSwap && oldOrderFrom == 1 && newOrderFrom == 1)
                {
                    delta = RunFinder.GetRunDelta(from, fromRow, to, toRow);
                }
                if (delta <= 0)
                {
                    return(false);
                }
            }

            return(true);
        }