public PointDTO GetSnakeNewHead(SnakeDTO snake, SizeDTO boardSize) { var index = Offsets.FindIndex(t => t.Direction == snake.Direction); var offset = Offsets[(index + MoveOffset + 4)%4]; var newHead = OffsetModulo(snake.Head, offset.Offset, boardSize); return newHead; }
private static PointDTO OffsetModulo(PointDTO p, Offset offset, SizeDTO boardSize) { return new PointDTO { X = (p.X + offset.DX + boardSize.Width)%boardSize.Width, Y = (p.Y + offset.DY + boardSize.Height)%boardSize.Height }; }
public int Distance(PointDTO head, PointDTO target, SizeDTO size) { var trans = new[] { new {X = 0, Y = 0}, new {X = 1, Y = 0}, new {X = -1, Y = 0}, new {X = 0, Y = 1}, new {X = 0, Y = -1} }; var heads = trans.Select(t => new PointDTO { X = t.X * size.Width + head.X, Y = t.Y * size.Height + head.Y }); return heads.Min(h => Distance(h, target)); }
private Move GetPrefferedDirection(IEnumerable<PointDTO> food, List<Move> moves, SnakeDTO mySnake, SizeDTO boardSize) { var foodGroup = food.Select(f => new { Food = f, Metric = (Distance(mySnake.Head, f, boardSize) - NumOfNeigh(food, f) * 2) }); var closestFoods = foodGroup.OrderBy(f => f.Metric).Select(f => f.Food); if (!closestFoods.Any()) { return Move.None; } var closestFood = closestFoods.First(); return moves.OrderBy(f => Distance(f.GetSnakeNewHead(mySnake, boardSize), closestFood)).First(); }