private static List <Card> TryBuildDeck(List <Card> cards, CardRatings cardRatings) { var deck = new List <Card>(); var creatures = cards .Where(x => x.Is().Creature) .OrderByDescending(x => cardRatings.GetRating(x.Name)) .ToList(); var bestCreatures = creatures .Take(MinCreatureCount); var otherCreatures = creatures.Skip(MinCreatureCount) .Take(MaxCreatureCount - MinCreatureCount); var spellsAndOtherCreatures = cards .Where(x => !x.Is().Creature&& !x.Is().Land) .Concat(otherCreatures) .OrderByDescending(x => cardRatings.GetRating(x.Name)); deck.AddRange(bestCreatures); deck.AddRange(spellsAndOtherCreatures.Take(MaxSpellCount - deck.Count)); if (deck.Count < MinSpellCount) { return(null); } return(AddLands(deck, cards, cardRatings)); }
private static void RemoveWorstCards(List <Card> deckNoLands, int count, CardRatings cardRatings) { var cardsToRemove = deckNoLands .OrderBy(x => cardRatings.GetRating(x.Name)) .Take(count); foreach (var card in cardsToRemove) { deckNoLands.Remove(card); } }
private static void AddNonBasicLands(List <int> distribution, List <Card> library, List <Card> deck, CardRatings cardRatings) { var nonBasicLands = library.Where(x => x.Is().Land).ToList(); var deckColors = distribution.Select((x, i) => x > 0 ? i : -1).Where(x => x >= 0).ToList(); var maxCountColor = distribution.IndexOf(distribution.Max()); var landsToReplaceBasic = new List <Card>(); foreach (var land in nonBasicLands) { var rating = cardRatings.GetRating(land.Name); if (rating < MinNonBasicLandRating) { continue; } var landColors = land.ProducableManaColors; if (landColors.Count == 1) { if (deckColors.Contains(landColors[0])) { distribution[landColors[0]]--; landsToReplaceBasic.Add(land); } } else if (landColors.Count > 1) { var matchCount = landColors.Count(deckColors.Contains); if (matchCount >= 2) { distribution[maxCountColor]--; landsToReplaceBasic.Add(land); } } } deck.AddRange(landsToReplaceBasic); }
private static void AddNonBasicLands(List<int> distribution, List<Card> library, List<Card> deck, CardRatings cardRatings) { var nonBasicLands = library.Where(x => x.Is().Land).ToList(); var deckColors = distribution.Select((x, i) => x > 0 ? i : -1).Where(x => x >= 0).ToList(); var maxCountColor = distribution.IndexOf(distribution.Max()); var cardsToRemoveCount = 0; var landsToReplaceBasic = new List<Card>(); foreach (var land in nonBasicLands) { var rating = cardRatings.GetRating(land.Name); if (rating < MinNonBasicLandRating) continue; var landColors = land.ProducableManaColors; if (landColors.Count == 0) { deck.Add(land); cardsToRemoveCount++; } if (landColors.Count == 1) { if (deckColors.Contains(landColors[0])) { distribution[landColors[0]]--; landsToReplaceBasic.Add(land); } else if (landColors[0] == (int) CardColor.Colorless) { if (deckColors.Count > 1) { deck.Add(land); cardsToRemoveCount++; } else { distribution[maxCountColor]--; landsToReplaceBasic.Add(land); } } } else if (landColors.Count > 1) { var matchCount = landColors.Count(deckColors.Contains); if (matchCount >= 2) { distribution[maxCountColor]--; landsToReplaceBasic.Add(land); } } } if (cardsToRemoveCount > 0) { // Some lands do not replace existing lands // e.g if they do not produce mana. // For each such land remove worst cards from deck // so that deck count will be 40. RemoveWorstCards(deck, cardsToRemoveCount, cardRatings); } deck.AddRange(landsToReplaceBasic); }
private static List<Card> TryBuildDeck(List<Card> cards, CardRatings cardRatings) { var deck = new List<Card>(); var creatures = cards .Where(x => x.Is().Creature) .OrderByDescending(x => cardRatings.GetRating(x.Name)) .ToList(); var bestCreatures = creatures .Take(MinCreatureCount); var otherCreatures = creatures.Skip(MinCreatureCount) .Take(MaxCreatureCount - MinCreatureCount); var spellsAndOtherCreatures = cards .Where(x => !x.Is().Creature && !x.Is().Land) .Concat(otherCreatures) .OrderByDescending(x => cardRatings.GetRating(x.Name)); deck.AddRange(bestCreatures); deck.AddRange(spellsAndOtherCreatures.Take(MaxSpellCount - deck.Count)); if (deck.Count < MinSpellCount) return null; return AddLands(deck, cards, cardRatings); }
private static void RemoveWorstCards(List<Card> deckNoLands, int count, CardRatings cardRatings) { var cardsToRemove = deckNoLands .OrderBy(x => cardRatings.GetRating(x.Name)) .Take(count); foreach (var card in cardsToRemove) { deckNoLands.Remove(card); } }
private static DeckCandidate BuildDeck(List <Card> cards, CardRatings cardRatings) { var deck = new List <Card>(); var creatures = cards .Where(x => x.Is().Creature) .Select(x => { var convertedCost = x.ConvertedCost; if (convertedCost <= 2) { convertedCost = 2; } if (convertedCost >= 6) { convertedCost = 6; } return(new { Card = x, ConvertedCost = convertedCost, Rating = cardRatings.GetRating(x.Name) }); }) .GroupBy(x => x.ConvertedCost) .OrderBy(x => x.Key) .Select(x => { var cost = x.Key; var maxCreatureCount = CreaturesManaCurve[cost - 2]; var ordered = x.OrderByDescending(y => y.Rating) .ToList(); var selected = ordered .Take(maxCreatureCount) .Where(y => y.Rating > PlayableThreshold) .Select(y => new { y.Card, y.Rating }) .ToList(); var skipped = ordered .Where(y => !selected.Any(z => z.Card == y.Card)) .Select(y => new { y.Card, y.Rating }) .ToList(); return(new { Selected = selected, Skipped = skipped }); }) .ToList(); var selectedCreatures = creatures .SelectMany(x => x.Selected) .ToList(); var remaining = creatures .SelectMany(x => x.Skipped) .Concat(cards .Where(x => !x.Is().Creature&& !x.Is().Land) .Select(x => new { Card = x, Rating = cardRatings.GetRating(x.Name) })) .OrderByDescending(x => x.Rating) .ToList(); var selectedRemaining = remaining. Take(SpellCount - selectedCreatures.Count) .ToList(); var avarageRating = selectedCreatures.Concat(selectedRemaining) .Average(x => x.Rating); deck.AddRange(selectedCreatures.Select(x => x.Card)); deck.AddRange(selectedRemaining.Select(x => x.Card)); var spellCount = deck.Count; var landCount = DeckCardCount - spellCount; deck = AddLands(deck, cards, cardRatings, landCount); return(new DeckCandidate(deck, spellCount, avarageRating)); }
private static void AddNonBasicLands(List <int> distribution, List <Card> library, List <Card> deck, CardRatings cardRatings) { var nonBasicLands = library.Where(x => x.Is().Land).ToList(); var deckColors = distribution.Select((x, i) => x > 0 ? i : -1).Where(x => x >= 0).ToList(); var maxCountColor = distribution.IndexOf(distribution.Max()); var cardsToRemoveCount = 0; var landsToReplaceBasic = new List <Card>(); foreach (var land in nonBasicLands) { var rating = cardRatings.GetRating(land.Name); if (rating < MinNonBasicLandRating) { continue; } var landColors = land.ProducableManaColors; if (landColors.Count == 0) { deck.Add(land); cardsToRemoveCount++; } if (landColors.Count == 1) { if (deckColors.Contains(landColors[0])) { distribution[landColors[0]]--; landsToReplaceBasic.Add(land); } else if (landColors[0] == (int)CardColor.Colorless) { if (deckColors.Count > 1) { deck.Add(land); cardsToRemoveCount++; } else { distribution[maxCountColor]--; landsToReplaceBasic.Add(land); } } } else if (landColors.Count > 1) { var matchCount = landColors.Count(deckColors.Contains); if (matchCount >= 2) { distribution[maxCountColor]--; landsToReplaceBasic.Add(land); } } } if (cardsToRemoveCount > 0) { // Some lands do not replace existing lands // e.g if they do not produce mana. // For each such land remove worst cards from deck // so that deck count will be 40. RemoveWorstCards(deck, cardsToRemoveCount, cardRatings); } deck.AddRange(landsToReplaceBasic); }