Advertisement
Guest User

Untitled

a guest
Dec 20th, 2024
211
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Python 2.74 KB | None | 0 0
  1. from pathlib import Path
  2. from collections import deque
  3.  
  4.  
  5. def parse_data(file_name):
  6.     """Read and process the grid data from the file."""
  7.     file_path = Path(__file__).resolve().parent / f"{file_name}.txt"
  8.     with open(file_path, "r") as f:
  9.         grid = [line.strip() for line in f]
  10.  
  11.     paths = set()
  12.     end = None
  13.     for y, row in enumerate(grid):
  14.         for x, cell in enumerate(row):
  15.             if cell != "#":
  16.                 paths.add((x, y))
  17.                 if cell == "E":
  18.                     end = (x, y)
  19.     return end, paths
  20.  
  21.  
  22. def get_distances(start_point, paths):
  23.     """Compute distances using BFS."""
  24.     directions = [(0, 1), (0, -1), (1, 0), (-1, 0)]
  25.     distances = {start_point: 0}
  26.     queue = deque([start_point])
  27.  
  28.     while queue:
  29.         x, y = queue.popleft()
  30.         current_distance = distances[(x, y)]
  31.         for dx, dy in directions:
  32.             neighbor = (x + dx, y + dy)
  33.             if neighbor in paths and neighbor not in distances:
  34.                 distances[neighbor] = current_distance + 1
  35.                 queue.append(neighbor)
  36.     return distances
  37.  
  38.  
  39. def find_pairs_within_distance(points, threshold):
  40.     """Find pairs of points within the Manhattan distance threshold."""
  41.     pairs = []
  42.     if not points:
  43.         return pairs
  44.  
  45.     # Sort points by x-coordinate once
  46.     sorted_points = sorted(points, key=lambda p: p[0])
  47.     num_points = len(points)
  48.  
  49.     for i in range(num_points):
  50.         p1 = sorted_points[i]
  51.         j = i + 1
  52.  
  53.         # Check points that could be within threshold based on x-coordinate
  54.         while j < num_points and sorted_points[j][0] - p1[0] <= threshold:
  55.             p2 = sorted_points[j]
  56.             y_dist = abs(p2[1] - p1[1])
  57.             if y_dist <= threshold:
  58.                 dist = y_dist + abs(p2[0] - p1[0])
  59.                 if 1 < dist <= threshold:
  60.                     pairs.append((p1, p2, dist))
  61.             j += 1
  62.  
  63.     return pairs
  64.  
  65.  
  66. def calculate_time_savings(end_distances, pairs, min_save=100):
  67.     """Calculate time savings for pairs of points."""
  68.     time_savings = 0
  69.     for p1, p2, dist in pairs:
  70.         d1 = end_distances[p1]
  71.         d2 = end_distances[p2]
  72.         time_saved = abs(d1 - d2) - dist
  73.         if time_saved >= min_save:
  74.             time_savings += 1
  75.     return time_savings
  76.  
  77.  
  78. def main():
  79.     end, paths = parse_data("data")
  80.     end_distances = get_distances(end, paths)
  81.     valid_points = list(paths)
  82.  
  83.     for cheat_distance in [2, 20]:
  84.         pairs = find_pairs_within_distance(valid_points, cheat_distance)
  85.         total_savings = calculate_time_savings(end_distances, pairs)
  86.         print(f"Total time savings (distance {cheat_distance}):", total_savings)
  87.  
  88.  
  89. if __name__ == "__main__":
  90.     main()
  91.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement