|
|
@@ -0,0 +1,41 @@ |
|
|
|
import itertools |
|
|
|
import math |
|
|
|
import sys |
|
|
|
from functools import partial |
|
|
|
|
|
|
|
|
|
|
|
def measure(start, other): |
|
|
|
dx, dy = other[0] - start[0], other[1] - start[1] |
|
|
|
angle = math.atan2(-dx, dy) |
|
|
|
return -math.pi if angle == math.pi else angle, math.hypot(dx, dy), other |
|
|
|
|
|
|
|
|
|
|
|
def seek(start, asteroids): |
|
|
|
pending = sorted(measure(start, ast) for ast in asteroids) |
|
|
|
while pending: |
|
|
|
copy = pending.copy() |
|
|
|
pending = [] |
|
|
|
out = {} |
|
|
|
for angle, dist, ast in copy: |
|
|
|
if angle in out: |
|
|
|
pending.append((angle, dist, ast)) |
|
|
|
else: |
|
|
|
out[angle] = ast |
|
|
|
yield list(out.values()) |
|
|
|
|
|
|
|
|
|
|
|
text = sys.stdin.read() |
|
|
|
asteroids = { |
|
|
|
(X, Y) |
|
|
|
for Y, line in enumerate(text.splitlines()) |
|
|
|
for X, cell in enumerate(line) |
|
|
|
if cell == '#' |
|
|
|
} |
|
|
|
|
|
|
|
visibility = {ast: len(next(seek(ast, asteroids))) for ast in asteroids} |
|
|
|
origin = max(visibility, key=visibility.get) |
|
|
|
print(visibility[origin]) |
|
|
|
|
|
|
|
ordering = list(itertools.chain(*seek(origin, asteroids))) |
|
|
|
x, y = ordering[200 - 1] |
|
|
|
print(100 * x + y) |