Esempio n. 1
0
        public MultiMoves CalculateTakeTerritoriesMoves(List <TerritoryIDType> territoriesToTake, MultiMoves precondition)
        {
            MultiMoves             resultMoves           = precondition.Clone();
            List <TerritoryIDType> territoriesToTakeCopy = new List <TerritoryIDType>(territoriesToTake);


            while (territoriesToTakeCopy.Count > 0)
            {
                var reachableTerritories = FilterNonBorderingTerritories(territoriesToTakeCopy, resultMoves);
                if (reachableTerritories.Count == 0)
                {
                    return(null);
                }
                var bestStartTerritory  = GetBestAttackingTerritory(reachableTerritories, resultMoves);
                var bestAttackTerritory = GetBestAttackTerritory(reachableTerritories, territoriesToTakeCopy, bestStartTerritory, resultMoves);
                int neededAttackArmies  = AttackInformer.GetNeededBreakArmies
                                              (resultMoves.GetTerritoryStandingsAfterAllMoves()[bestAttackTerritory].NumArmies.ArmiesOrZero);
                GameOrderAttackTransfer attackOrder = GameOrderAttackTransfer.Create
                                                          (GameState.MyPlayerId, bestStartTerritory, bestAttackTerritory, AttackTransferEnum.AttackTransfer, new Armies(neededAttackArmies), REASON);

                var  standing       = resultMoves.GetTerritoryStandingsAfterAllMoves().Where(o => o.Key == attackOrder.From).First().Value;
                int  leftoverArmies = standing.NumArmies.ArmiesOrZero - standing.ArmiesMarkedAsUsed.ArmiesOrZero - 1;
                int  armiesToPump   = Math.Max(0, attackOrder.NumArmies.ArmiesOrZero - leftoverArmies);
                bool successfull    = resultMoves.PumpArmies(attackOrder.From, armiesToPump, REASON);
                if (!successfull)
                {
                    return(null);
                }
                resultMoves.AddAttackOrder(attackOrder);
                territoriesToTakeCopy.Remove(bestAttackTerritory);
            }

            return(resultMoves);
        }
Esempio n. 2
0
        public MultiMoves CalculateMoveArmiesToBorderMoves(MultiMoves presentMoves)
        {
            MultiMoves result = presentMoves.Clone();
            var        nonOwnedTerritories = MapInformer.GetNonOwnedTerritories(result.GetTerritoryStandingsAfterAllMoves().Values.ToList(), GameState.MyPlayerId);
            var        keys = new List <TerritoryIDType>();

            nonOwnedTerritories.ForEach(k => keys.Add(k.ID));
            var distances = MapInformer.GetDistancesFromTerritories(keys);

            foreach (TerritoryIDType territoryId in distances.Keys)
            {
                int distance = distances[territoryId];
                if (distance <= 1)
                {
                    continue;
                }
                var neighbors = MapInformer.GetNeighborTerritories(territoryId);
                var lowestDistanceNeighborValue = neighbors.Min(c => distances[c]);
                var lowestDistanceNeighbor      = neighbors.Where(n => distances[n] == lowestDistanceNeighborValue).First();
                TerritoryStanding theTerritory  = result.GetTerritoryStandingsAfterAllMoves()[territoryId];
                int armiesAvailable             = theTerritory.NumArmies.ArmiesOrZero - theTerritory.ArmiesMarkedAsUsed.ArmiesOrZero - 1;
                if (armiesAvailable == 0)
                {
                    continue;
                }
                GameOrderAttackTransfer attackMove =
                    GameOrderAttackTransfer.Create
                        (GameState.MyPlayerId, territoryId, lowestDistanceNeighbor, AttackTransferEnum.AttackTransfer, new Armies(armiesAvailable), REASON);
                result.AddAttackOrder(attackMove);
            }
            return(result);
        }
Esempio n. 3
0
        public void AddAttackOrder(GameOrderAttackTransfer attackOrder)
        {
            standingCache = null;
            var alreadyPresentAttackMove = AttackMoves.Where(a => a.From == attackOrder.From && a.To == attackOrder.To).FirstOrDefault();

            if (alreadyPresentAttackMove == null)
            {
                AttackMoves.Add(attackOrder);
            }
            else
            {
                alreadyPresentAttackMove.NumArmies = new Armies(alreadyPresentAttackMove.NumArmies.ArmiesOrZero + attackOrder.NumArmies.ArmiesOrZero);
            }
        }
Esempio n. 4
0
        private int GetClassification(GameOrderAttackTransfer attackMove)
        {
            var  initialState              = GameState.CurrentTurn().LatestTurnStanding.Territories;
            bool opponentAttack            = initialState[attackMove.To].OwnerPlayerID == GameState.OpponentPlayerId;
            var  attackFromNeighbors       = MapInformer.GetNeighborTerritories(initialState[attackMove.From].ID);
            var  opponentTerritories       = MapInformer.GetOwnedTerritories(initialState.Values.ToList(), GameState.OpponentPlayerId);
            var  opponentNeighboringAttack = false;

            foreach (var opponentTerritory in opponentTerritories)
            {
                if (attackFromNeighbors.Contains(opponentTerritory.ID))
                {
                    opponentNeighboringAttack = true;
                }
            }
            bool clearOpponentBreak = false;
            int  opponentIncome     = GameState.CurrentTurn().Incomes[GameState.OpponentPlayerId].FreeArmies;
            int  maxOpponentArmies  = 0;

            if (opponentAttack)
            {
                maxOpponentArmies = initialState[attackMove.To].NumArmies.ArmiesOrZero + opponentIncome;
                int maxNeededArmies = AttackInformer.GetNeededBreakArmies(maxOpponentArmies);
                if (attackMove.NumArmies.ArmiesOrZero >= maxNeededArmies)
                {
                    clearOpponentBreak = true;
                }
            }
            bool isTransfer  = initialState[attackMove.To].OwnerPlayerID == GameState.MyPlayerId;
            bool isExpansion = initialState[attackMove.To].IsNeutral;

            if (clearOpponentBreak)
            {
                return(1);
            }
            if (isTransfer)
            {
                return(2);
            }
            if (isExpansion && !opponentNeighboringAttack)
            {
                return(3);
            }
            if (isExpansion && opponentNeighboringAttack)
            {
                return(4);
            }
            // non clear opponent attacks
            return(5);
        }
Esempio n. 5
0
        private GameOrderAttackTransfer GetBiggestAttackMove(MultiMoves movesSoFar)
        {
            if (movesSoFar.AttackMoves.Count() == 0)
            {
                return(null);
            }
            GameOrderAttackTransfer biggestAttack = movesSoFar.AttackMoves.First();

            foreach (GameOrderAttackTransfer attackMove in movesSoFar.AttackMoves)
            {
                if (attackMove.NumArmies.ArmiesOrZero > biggestAttack.NumArmies.ArmiesOrZero)
                {
                    biggestAttack = attackMove;
                }
            }
            return(biggestAttack);
        }
Esempio n. 6
0
        public MultiMoves CalculateNoPlanMoves(MultiMoves presentMoves)
        {
            MultiMoves resultMoves = presentMoves.Clone();
            // we currently assume the biggest attack has to start from an owned territory
            GameOrderAttackTransfer biggestAttack = GetBiggestAttackMove(resultMoves);
            int stillAvailableDeployment          = GameState.CurrentTurn().GetMyIncome() - resultMoves.GetCurrentDeployment();

            if (biggestAttack != null)
            {
                PumpBiggestAttack(resultMoves, biggestAttack, stillAvailableDeployment);
            }
            else
            {
                AddBorderTerritoryDeployment(resultMoves, stillAvailableDeployment);
            }
            return(resultMoves);
        }
Esempio n. 7
0
        private void AddAttack(TerritoryIDType from, TerritoryIDType to, AttackTransferEnum attackTransfer, int numArmies, bool attackTeammates)
        {
            IEnumerable <GameOrderAttackTransfer> attacks = Orders.OfType <GameOrderAttackTransfer>();
            var existingFrom   = attacks.Where(o => o.From == from).ToList();
            var existingFromTo = existingFrom.Where(o => o.To == to).ToList();

            if (existingFromTo.Any())
            {
                existingFromTo.Single().NumArmies = existingFromTo.Single().NumArmies.Add(new Armies(numArmies));
            }
            else
            {
                var specials = Standing.Territories[from].NumArmies.SpecialUnits;
                if (specials.Length > 0)
                {
                    var used = existingFrom.SelectMany(o => o.NumArmies.SpecialUnits).Select(o => o.ID).ToHashSet(false);
                    specials = specials.Where(o => used.Contains(o.ID) == false).ToArray();
                }

                AddOrder(GameOrderAttackTransfer.Create(this.PlayerID, from, to, attackTransfer, false, new Armies(numArmies, false, specials), attackTeammates));
            }
        }
Esempio n. 8
0
        // Returns an already calculated attack path from an owned territory to a territory in the path to which we want to pump extra deployment.
        private List <GameOrderAttackTransfer> GetPumpPath(TerritoryIDType territoryToPumpTo)
        {
            // we can't pump from transfer moves
            GameStanding           gameStanding     = GameState.CurrentTurn().LatestTurnStanding;
            List <TerritoryIDType> ownedTerritories = gameStanding.Territories.Values.Where(o => o.OwnerPlayerID == GameState.MyPlayerId).Select(o => o.ID).ToList();
            var attackMoves = AttackMoves.Where(o => !ownedTerritories.Contains(o.To)).ToList();

            List <GameOrderAttackTransfer> pumpPath = new List <GameOrderAttackTransfer>();
            TerritoryIDType currentPumpToTerritory  = territoryToPumpTo;

            while (true)
            {
                if (ownedTerritories.Contains(currentPumpToTerritory))
                {
                    break;
                }
                GameOrderAttackTransfer pumpOrder = attackMoves.Find(o => o.To == currentPumpToTerritory);
                pumpPath.Insert(0, pumpOrder);
                currentPumpToTerritory = pumpOrder.From;
            }
            return(pumpPath);
        }
Esempio n. 9
0
        private void PumpBiggestAttack(MultiMoves movesSoFar, GameOrderAttackTransfer biggestAttack, int availableDeployment)
        {
            if (availableDeployment == 0)
            {
                return;
            }
            movesSoFar.AddDeployOrder(GameOrderDeploy.Create(GameState.MyPlayerId, availableDeployment, biggestAttack.From, REASON));
            var  endAttack = biggestAttack;
            bool foundStep = true;

            while (foundStep)
            {
                foundStep = false;
                // probably endless loop possible as soon as we add transfer moves back to attacking territory
                var nextAttack = movesSoFar.AttackMoves.Where(a => a.From == endAttack.To).FirstOrDefault();
                if (nextAttack != null)
                {
                    endAttack = nextAttack;
                    foundStep = true;
                }
            }
            movesSoFar.PumpArmies(endAttack.To, availableDeployment, REASON);
        }
Esempio n. 10
0
        public void AddAttack(TerritoryIDType from, TerritoryIDType to, AttackTransferEnum attackTransfer, int numArmies, bool attackTeammates, bool byPercent = false, bool bosses = false, bool commanders = false)
        {
            Assert.Fatal(Bot.Map.Territories[from].ConnectedTo.ContainsKey(to), from + " does not connect to " + to);

            var actualArmies    = numArmies;
            var actualByPercent = byPercent;

            if (actualByPercent && Bot.Settings.AllowPercentageAttacks == false)
            {
                actualByPercent = false;
                actualArmies    = 1000000;
            }

            var actualMode = attackTransfer;

            if (actualMode == AttackTransferEnum.Transfer && Bot.Settings.AllowTransferOnly == false)
            {
                actualMode = AttackTransferEnum.AttackTransfer;
            }
            if (actualMode == AttackTransferEnum.Attack && Bot.Settings.AllowAttackOnly == false)
            {
                actualMode = AttackTransferEnum.AttackTransfer;
            }

            IEnumerable <GameOrderAttackTransfer> attacks = Orders.OfType <GameOrderAttackTransfer>();
            var existingFrom   = attacks.Where(o => o.From == from).ToList();
            var existingFromTo = existingFrom.Where(o => o.To == to).ToList();

            if (existingFromTo.Any())
            {
                var existing = existingFromTo.Single();
                existing.ByPercent      = actualByPercent;
                existing.AttackTransfer = actualMode;
                existing.NumArmies      = existing.NumArmies.Add(new Armies(actualArmies));

                if (actualByPercent && existing.NumArmies.NumArmies > 100)
                {
                    existing.NumArmies = existing.NumArmies.Subtract(new Armies(existing.NumArmies.NumArmies - 100));
                }
            }
            else
            {
                var specials = Bot.Standing.Territories[from].NumArmies.SpecialUnits;
                if (specials.Length > 0)
                {
                    var used = existingFrom.SelectMany(o => o.NumArmies.SpecialUnits).Select(o => o.ID).ToHashSet(false);
                    specials = specials.Where(o => used.Contains(o.ID) == false).ToArray();

                    if (bosses == false)
                    {
                        specials = specials.Where(o => o.IsBoss() == false).ToArray();
                    }

                    if (commanders == false)
                    {
                        specials = specials.Where(o => !(o is Commander)).ToArray();
                    }
                }

                AddOrder(GameOrderAttackTransfer.Create(Bot.PlayerID, from, to, actualMode, actualByPercent, new Armies(actualArmies, specials), attackTeammates));
            }
        }
Esempio n. 11
0
 private GameOrder Convert(BotOrderAttackTransfer o)
 {
     return(GameOrderAttackTransfer.Create(o.PlayerID, o.From.ID, o.To.ID, AttackTransferEnum.AttackTransfer, false, o.Armies, false));
 }
 public UtilizeSpareArmies(GameOrderAttackTransfer order, int available)
 {
     Order     = order;
     Available = available;
 }
Esempio n. 13
0
 private static GameOrder Convert(BotOrderAttackTransfer o)
 {
     return(GameOrderAttackTransfer.Create(o.PlayerID, o.FromTerritory.ID, o.ToTerritory.ID, AttackTransferEnum.AttackTransfer, false, new Armies(o.Armies), false));
 }