Пример #1
0
        protected PlayerAction BuyPhase(Player player)
        {
            // play all treasures
            foreach (CardModel card in player.Hand.ToList())
            {
                if (card.Is(CardType.Treasure))
                {
                    player.PlayTreasure(card);
                }
            }
            List<CardModel> deck = player.Hand.Union(player.Discard.Union(player.Played)).ToList();
            IEnumerable<Pile> availableBuys = (from pile in this.GameModel.SupplyPiles where pile.Count > 0 && this.GameModel.GetCost(pile) <= player.Coin && (!pile.CostsPotion || player.Potions > 0) select pile);
            double gamePhase = this.GetGamePhase();

            while (player.Buys > 0)
            {
                Pile bestBuy = null;
                List<double> evals = new List<double>();
                List<double> handEvals = new List<double>();
                double bestScore = double.MinValue;

                foreach (Pile pile in availableBuys)
                {
                    if (pile.Count == 0 || this.GameModel.GetCost(pile) > player.Coin || (pile.CostsPotion && player.Potions == 0)) continue;

                    double eval = this.StaticEvalSimple(pile.Card, gamePhase);
                    if (eval > bestScore)
                    {
                        bestScore = eval;
                        bestBuy = pile;
                    }

                    evals.Add(this.StaticEvalSimple(pile.Card, gamePhase));

                    double handEval = 0;
                    for (int i = 0; i < 10; i++)
                    {
                        List<CardModel> cards = new List<CardModel>();
                        cards.Add(pile.Card);
                        for (int j = 0; j < 4; j++)
                        {
                            cards.Add(deck[((i + j) * 153431) % deck.Count]);
                        }
                        handEval += this.EvaulateHand(cards, gamePhase);
                    }
                    handEvals.Add(handEval);
                }

                double minEval = double.MaxValue, maxEval = double.MinValue;
                double minHandEval = double.MaxValue, maxHandEval = double.MinValue;

                foreach (double eval in evals)
                {
                    minEval = Math.Min(eval, minEval);
                    maxEval = Math.Max(eval, maxEval);
                }

                foreach (double eval in handEvals)
                {
                    minHandEval = Math.Min(eval, minHandEval);
                    maxHandEval = Math.Max(eval, maxHandEval);
                }

                int index = 0;
                foreach (Pile pile in availableBuys)
                {
                    if (pile.Count == 0 || this.GameModel.GetCost(pile) > player.Coin || (pile.CostsPotion && this.Player.Potions == 0)) continue;

                    double score = 0;
                    score += ((evals[index] - minEval) / (maxEval - minEval));
                    //					score += ((handEvals[index] - minHandEval) / (maxHandEval - minHandEval));

                    if (score > bestScore && evals[index] > 0.0)
                    {
                        bestScore = score;
                        bestBuy = pile;
                    }

                    index++;
                }

                if (bestBuy == null)
                {
                    break;
                }
                return new PlayerAction() { ActionType = Dominion.ActionType.BuyCard, Pile = bestBuy };
            }
            return new PlayerAction();
        }