コード例 #1
0
        public void Charge(AVehicle veh)
        {
            if (!veh.CanChargeFacility)
            {
                return;
            }

            if (veh.IsMy)
            {
                if (CapturePoints < G.MaxFacilityCapturePoints && ContainsPoint(veh))
                {
                    CapturePoints += G.FacilityCapturePointsPerVehiclePerTick;
                    if (CapturePoints > G.MaxFacilityCapturePoints)
                    {
                        CapturePoints = G.MaxFacilityCapturePoints;
                    }
                }
            }
            else
            {
                if (CapturePoints > -G.MaxFacilityCapturePoints && ContainsPoint(veh))
                {
                    CapturePoints -= G.FacilityCapturePointsPerVehiclePerTick;
                    if (CapturePoints < -G.MaxFacilityCapturePoints)
                    {
                        CapturePoints = -G.MaxFacilityCapturePoints;
                    }
                }
            }
        }
コード例 #2
0
        public void UpdateVehicle(AVehicle cur, AVehicle from)
        {
            var prevX = cur.X;
            var prevY = cur.Y;

            cur.CopyFrom(from);
            _updateVehicleCoordinates(cur, prevX, prevY);
        }
コード例 #3
0
ファイル: AVehicle.cs プロジェクト: wampirr/AiCup
 public void CopyFrom(AVehicle unit)
 {
     Radius = unit.Radius;
     X      = unit.X;
     Y      = unit.Y;
     Id     = unit.Id;
     _copyFrom(unit);
 }
コード例 #4
0
ファイル: AVehicle.cs プロジェクト: wampirr/AiCup
        public int GetAttackDamage2(AVehicle veh, double additionalRadius = 0)
        {
            var attackRange = Geom.Sqr(G.AttackRange[(int)Type, (int)veh.Type] + additionalRadius);

            if (GetDistanceTo2(veh) - Const.Eps > attackRange)
            {
                return(0);
            }
            return(G.AttackDamage[(int)Type, (int)veh.Type]);
        }
コード例 #5
0
ファイル: AVehicle.cs プロジェクト: wampirr/AiCup
        public int GetAttackDamage(AVehicle veh, double additionalRadius = 0)
        {
            var damage = GetAttackDamage2(veh, additionalRadius);

            if (damage >= veh.Durability)
            {
                return(veh.Durability);
            }
            return(damage);
        }
コード例 #6
0
 private static bool _isVehicleVisible(Sandbox env, AVehicle veh)
 {
     foreach (var x in env.GetMyNeighbours(veh.X, veh.Y, 120 * veh.StealthFactor))
     {
         if (x.IsVisible(veh))
         {
             return(true);
         }
     }
     return(false);
 }
コード例 #7
0
ファイル: AVehicle.cs プロジェクト: wampirr/AiCup
        public void Attack(AVehicle veh)
        {
            if (RemainingAttackCooldownTicks > 0)
            {
                return;
            }

            var damage = GetAttackDamage(veh);

            veh.Durability -= damage;
            RemainingAttackCooldownTicks = G.AttackCooldownTicks;
        }
コード例 #8
0
        private static void _fillStartingPosition(IEnumerable <AVehicle> myVehicles)
        {
            foreach (var my in myVehicles)
            {
                var clone = new AVehicle(my);
                clone.X    = G.MapSize - clone.X;
                clone.Y    = G.MapSize - clone.Y;
                clone.IsMy = !clone.IsMy;
                clone.Id  *= -1;

                OppUncheckedVehicles[clone.Id] = clone;
                _idsPool[(int)clone.Type].Add(clone.Id);
            }
        }
コード例 #9
0
 public void AddVehicleGroup(AVehicle veh, int groupId)
 {
     if (veh.HasGroup(groupId))
     {
         return;
     }
     veh.AddGroup(groupId);
     if (veh.IsMy)
     {
         while (_myVehiclesByGroup.Count < groupId)
         {
             _myVehiclesByGroup.Add(new List <AVehicle>());
         }
         _myVehiclesByGroup[groupId - 1].Add(veh);
     }
 }
コード例 #10
0
ファイル: AVehicle.cs プロジェクト: wampirr/AiCup
        private void _copyFrom(AVehicle unit)
        {
            IsMy       = unit.IsMy;
            Type       = unit.Type;
            Durability = unit.Durability;
            IsSelected = unit.IsSelected;
            RemainingAttackCooldownTicks = unit.RemainingAttackCooldownTicks;
            Groups            = unit.Groups;
            CanChargeFacility = unit.CanChargeFacility;

            Action = unit.Action;
            MoveVectorOrRotationCenter = unit.MoveVectorOrRotationCenter;
            MoveSpeedOrAngularSpeed    = unit.MoveSpeedOrAngularSpeed;
            MoveLengthOrRotationAngle  = unit.MoveLengthOrRotationAngle;

            DurabilityPool = unit.DurabilityPool;
        }
コード例 #11
0
        public bool DoMoveApprox(AVehicle[] vehicles, bool moveApprox)
        {
            var result = true;

            if (moveApprox)
            {
                Logger.CumulativeOperationStart("DoMoveA");
                for (var i = 0; i < vehicles.Length; i++)
                {
                    var veh = vehicles[i];
                    if (_prevStateCache[i] == null)
                    {
                        _prevStateCache[i] = new AVehicle(veh);
                    }
                    else
                    {
                        _prevStateCache[i].CopyFrom(veh);
                    }

                    if (!veh.Move())
                    {
                        // откатываем изменения
                        for (var j = 0; j < i; j++)
                        {
                            var prevX = vehicles[j].X;
                            var prevY = vehicles[j].Y;
                            vehicles[j].CopyFrom(_prevStateCache[j]);
                            _updateVehicleCoordinates(vehicles[j], prevX, prevY);
                        }
                        result = false;
                        break;
                    }
                    _updateVehicleCoordinates(veh, _prevStateCache[i].X, _prevStateCache[i].Y);
                }
                Logger.CumulativeOperationEnd("DoMoveA");
            }
            else
            {
                Logger.CumulativeOperationStart("DoMove1");
                _doMove1(vehicles);
                Logger.CumulativeOperationEnd("DoMove1");
            }
            return(result);
        }
コード例 #12
0
        private void _updateVehicleCoordinates(AVehicle veh, double prevX, double prevY)
        {
            var unitTree = _trees[veh.IsMy ? 1 : 0, veh.IsAerial ? 1 : 0];

            if (unitTree == null)
            {
                return; // Дерево ещё не создано. Когда будет создаваться - тогда и наполнится обновленными данными.
            }
            var moveX = veh.X;
            var moveY = veh.Y;

            if (!Geom.PointsEquals(prevX, prevY, moveX, moveY))
            {
                veh.X = prevX;
                veh.Y = prevY;

                if (!unitTree.ChangeXY(veh, moveX, moveY))
                {
                    throw new Exception("Can't change unit coordinates, id=" + veh.Id);
                }
            }
        }
コード例 #13
0
        private double _nuclearGetDamage(AVehicle veh, Sandbox env, double lowerBound, List <AVehicle> targets, out ANuclear nuclearResult)
        {
            var vr  = veh.ActualVisionRange * 0.9;
            var cen = Utility.Average(targets);

            cen = veh + (cen - veh).Normalized() * Math.Min(vr, veh.GetDistanceTo(cen));
            var nuclear = new ANuclear(cen.X, cen.Y, true, veh.Id, G.TacticalNuclearStrikeDelay);

            nuclearResult = nuclear;

            var totalOpponentDamage = targets.Sum(x => x.GetNuclearDamage(nuclear));

            if (totalOpponentDamage <= lowerBound)
            {
                return(totalOpponentDamage);
            }

            var totalDamage = totalOpponentDamage -
                              env.GetMyNeighbours(nuclear.X, nuclear.Y, nuclear.Radius)
                              .Sum(x => x.GetNuclearDamage(nuclear));

            return(totalDamage);
        }
コード例 #14
0
ファイル: AVehicle.cs プロジェクト: wampirr/AiCup
 public AVehicle(AVehicle unit) : base(unit)
 {
     _copyFrom(unit);
 }
コード例 #15
0
        private void _doMove1(AVehicle[] vehicles)
        {
            var unblockedLength = 0;

            for (var i = 0; i < vehicles.Length; i++)
            {
                var veh = vehicles[i];
                if (veh.Action == AVehicle.MoveType.None)
                {
                    veh.Move();
                    _complete[i] = true;
                    continue;
                }
                if (_movedState[i] == null)
                {
                    _movedState[i] = new AVehicle(veh);
                }
                else
                {
                    _movedState[i].CopyFrom(veh);
                }

                if (!_movedState[i].Move())
                {
                    veh.CopyFrom(_movedState[i]);
                    _complete[i] = true;
                    continue;
                }

                _unblocked[unblockedLength++] = i;
                _complete[i] = false;
                veh.Index    = i;

                if (_deps[i] == null)
                {
                    _deps[i] = new int[MagicMaxDependenciesCount];
                }
                _depsLen[i] = 0;
            }

            while (unblockedLength > 0)
            {
                var unblockedNewLength = 0;

                for (var i = 0; i < unblockedLength; i++)
                {
                    var idx       = _unblocked[i];
                    var movedUnit = _movedState[idx];
                    var unitTree  = _tree(movedUnit.IsMy, movedUnit.IsAerial);
                    var oppTree   = _tree(!movedUnit.IsMy, movedUnit.IsAerial);

                    var intersectsWith = -1;

                    do
                    {
                        {
                            var nearest = unitTree.FindFirstNearby(movedUnit, Geom.Sqr(2 * movedUnit.Radius));

                            if (nearest != null)
                            {
                                if (nearest.IntersectsWith(movedUnit))
                                {
                                    intersectsWith = nearest.Index;
                                    break;
                                }
                            }
                        }

                        if (!movedUnit.IsAerial && CheckCollisionsWithOpponent)
                        {
                            var nearest = oppTree.FindFirstNearby(movedUnit, Geom.Sqr(2 * movedUnit.Radius));

                            if (nearest != null)
                            {
                                if (nearest.IntersectsWith(movedUnit))
                                {
                                    intersectsWith = nearest.Index;
                                    break;
                                }
                            }
                        }
                    } while (false);

                    if (intersectsWith != -1)
                    {
                        if (!_complete[intersectsWith])
                        {
                            _deps[intersectsWith][_depsLen[intersectsWith]++] = idx;
                        }
                    }
                    else
                    {
                        var unit  = vehicles[idx];
                        var prevX = unit.X;
                        var prevY = unit.Y;
                        unit.CopyFrom(movedUnit);

                        if (!Geom.PointsEquals(prevX, prevY, movedUnit.X, movedUnit.Y))
                        {
                            unit.X = prevX;
                            unit.Y = prevY;

                            if (!unitTree.ChangeXY(unit, movedUnit.X, movedUnit.Y))
                            {
                                throw new Exception("Can't change unit coordinates, id=" + unit.Id);
                            }


                            if (_nearestFightersCacheTick != null && _nearestFightersCacheTick[idx] != -1)
                            {
                                _nearestFightersCacheDist[idx] -= unit.GetDistanceTo(prevX, prevY);
                            }
                        }
                    }

                    if (intersectsWith == -1 || _complete[intersectsWith])
                    {
                        // resolve dependencies
                        _complete[idx] = true;
                        for (var k = 0; k < _depsLen[idx]; k++)
                        {
                            _unblocked2[unblockedNewLength++] = _deps[idx][k];
                        }
                    }
                }

                unblockedLength = unblockedNewLength;
                Utility.Swap(ref _unblocked, ref _unblocked2);
            }
        }
コード例 #16
0
ファイル: AVehicle.cs プロジェクト: wampirr/AiCup
        public bool IsVisible(AVehicle vehicle)
        {
            var visionRange = vehicle.ActualVisionRange * vehicle.StealthFactor;

            return(visionRange * visionRange + Const.Eps >= GetDistanceTo2(vehicle));
        }
コード例 #17
0
        public static void Update()
        {
            _disappearedIds.Clear();
            foreach (Vehicle vehicle in MyStrategy.World.NewVehicles)
            {
                _vehicleById[vehicle.Id] = vehicle;
                VehicleById[vehicle.Id]  = new AVehicle(vehicle);

                if (G.IsFogOfWarEnabled && vehicle.PlayerId != MyStrategy.Me.Id)
                {
                    if (vehicle.Id <= 1000 && !_visibleOnce.Contains(vehicle.Id))
                    {
                        var fakeId = _idsPool[(int)vehicle.Type].Last();
                        _idsPool[(int)vehicle.Type].Pop();

                        OppUncheckedVehicles.Remove(fakeId);
                        OppCheckedVehicles.Remove(fakeId);
                    }

                    OppCheckedVehicles.Remove(vehicle.Id);
                    OppUncheckedVehicles.Remove(vehicle.Id);

                    _visibleOnce.Add(vehicle.Id);
                }
            }

            foreach (VehicleUpdate vehicleUpdate in MyStrategy.World.VehicleUpdates)
            {
                var vehicleId = vehicleUpdate.Id;

                if (vehicleUpdate.Durability == 0)
                {
                    _vehicleById.Remove(vehicleId);
                    VehicleById.Remove(vehicleId);

                    _disappearedIds.Add(vehicleId);
                }
                else
                {
                    var veh = new Vehicle(_vehicleById[vehicleId], vehicleUpdate);
                    _vehicleById[vehicleId] = veh;
                    if (veh.PlayerId != MyStrategy.Me.Id)
                    {
                        OppCheckedVehicles.Remove(veh.Id);
                        OppUncheckedVehicles.Remove(veh.Id);
                    }
                }
            }

            var errorsCount = 0;

            foreach (var veh in _vehicleById.Values)
            {
                var prev = MoveObserver.BeforeMoveUnits.ContainsKey(veh.Id) ? MoveObserver.BeforeMoveUnits[veh.Id] : null;
                var cur  = VehicleById.ContainsKey(veh.Id) ? VehicleById[veh.Id] : null;

                var updatedVehicle = new AVehicle(veh);

                if (updatedVehicle.IsMy)
                {
                    if (prev != null)
                    {
                        AVehicle aveh = new AVehicle(prev);
                        if (!Geom.PointsEquals(prev, updatedVehicle)) // в local runner сдвинулся
                        {
                            aveh.Move();
                        }
                        if (!Geom.PointsEquals(aveh, updatedVehicle))
                        {
                            Console.WriteLine("Looks vehicle updated wrong (X, Y)");
                        }

                        if ((aveh.Action == AVehicle.MoveType.Move || aveh.Action == AVehicle.MoveType.Scale) && Geom.DoublesEquals(aveh.MoveLengthOrRotationAngle, 0) ||
                            aveh.Action == AVehicle.MoveType.Rotate && Geom.DoublesEquals(aveh.MoveLengthOrRotationAngle, 0))
                        {
                            aveh.ForgotTarget();
                        }
                        updatedVehicle.Action = aveh.Action;
                        updatedVehicle.MoveVectorOrRotationCenter = aveh.MoveVectorOrRotationCenter;
                        updatedVehicle.MoveSpeedOrAngularSpeed    = aveh.MoveSpeedOrAngularSpeed;
                        updatedVehicle.MoveLengthOrRotationAngle  = aveh.MoveLengthOrRotationAngle;
                        updatedVehicle.DurabilityPool             = cur.DurabilityPool;
                        //TODO: поддерживать DurabilityPool if (!updatedVehicle.IsMy)
                    }

                    // дополнительные проверки
                    if (prev != null && !Geom.PointsEquals(prev, updatedVehicle)) // в local runner сдвинулся
                    {
                        var tmp = new AVehicle(cur);
                        if (Geom.PointsEquals(prev, cur))
                        {
                            tmp = new AVehicle(prev);
                            tmp.Move();
                            errorsCount++;
                        }

                        if (!Geom.PointsEquals(tmp, updatedVehicle))
                        {
                            Console.WriteLine("Looks vehicle updated wrong (X, Y)");
                        }
                    }
                    else if (!Geom.PointsEquals(cur, updatedVehicle)) // мой сдвинулся, а в local runner нет
                    {
                        errorsCount++;
                        var tmp = new AVehicle(updatedVehicle);
                        tmp.Move();
                        if (!Geom.PointsEquals(cur, tmp))
                        {
                            Console.WriteLine("Looks vehicle updated wrong (X, Y)");
                        }
                    }
                }

                VehicleById[veh.Id] = updatedVehicle;


                if (cur != null && updatedVehicle.IsSelected != cur.IsSelected)
                {
                    Console.WriteLine("Looks vehicle updated wrong (IsSelected)");
                }
            }

            if (errorsCount > 0)
            {
                Logger.Log("Move errors count: " + errorsCount);
            }
        }
コード例 #18
0
 private static AVehicle _cloneVehicle(AVehicle vehicle)
 {
     return(new AVehicle(vehicle));
 }
コード例 #19
0
        private Tuple <double, AMove> _nuclearFindMove(Sandbox env, double selTotalDamage, bool checkOnly)
        {
            AMove selMove = null;

            for (var s = 0; s < GroupsManager.MyGroups.Count + MyUngroupedClusters.Count; s++)
            {
                var vehicles = s < GroupsManager.MyGroups.Count
                    ? env.GetVehicles(true, GroupsManager.MyGroups[s])
                    : MyUngroupedClusters[s - GroupsManager.MyGroups.Count];
                var myAvg = Utility.Average(vehicles);

                var vrg = G.VisionRange[(int)VehicleType.Fighter] + G.MaxTacticalNuclearStrikeDamage;

                var oppGroups = OppClusters
                                .Where(cl =>
                                       cl.Avg.GetDistanceTo(myAvg) < vrg &&
                                       cl.Any(x => env.VehicleById.ContainsKey(x.Id)))// пропускать полностью фантомные группы
                                .OrderBy(cl => cl.Avg.GetDistanceTo(myAvg))
                                .Take(3)
                                .ToArray();

                foreach (var veh in vehicles)
                {
                    if (!veh.IsSelected && MoveObserver.AvailableActions < 3)
                    {
                        continue;
                    }
                    if (veh.IsSelected && MoveObserver.AvailableActions < 2)
                    {
                        continue;
                    }

                    var vr = veh.ActualVisionRange * 0.9;

                    foreach (
                        var oppGroup in
                        new[] { env.GetOpponentNeighbours(veh.X, veh.Y, vr + G.TacticalNuclearStrikeRadius) }.Concat(oppGroups))
                    {
                        ANuclear nuclear;
                        var      totalDamage = _nuclearGetDamage(veh, env, selTotalDamage, oppGroup, out nuclear);

                        if (totalDamage <= selTotalDamage)
                        {
                            continue;
                        }

                        var vehNextMove = new AVehicle(veh);
                        for (var t = 0; t < 3; t++)
                        {
                            vehNextMove.Move();
                        }
                        if (vehNextMove.GetDistanceTo2(nuclear) + Const.Eps >= Geom.Sqr(vehNextMove.ActualVisionRange))
                        {
                            continue;
                        }

                        const int n = 10;
                        if (vehicles.Count > n)
                        {
                            var myDist2        = veh.GetDistanceTo2(nuclear);
                            var myNearestCount = vehicles.Count(x => x.GetDistanceTo2(nuclear) <= myDist2);
                            if (myNearestCount < n)
                            {
                                continue;
                            }
                        }

                        selTotalDamage = totalDamage;
                        selMove        = new AMove
                        {
                            Action    = ActionType.TacticalNuclearStrike,
                            VehicleId = veh.Id,
                            Point     = nuclear,
                        };

                        if (checkOnly)
                        {
                            return(new Tuple <double, AMove>(selTotalDamage, selMove));
                        }
                    }
                }
            }

            if (selMove == null)
            {
                return(null);
            }

            return(new Tuple <double, AMove>(selTotalDamage, selMove));
        }