day 12, knowing what part1 has built, part2 was longer than expected
This commit is contained in:
parent
38f158b30d
commit
ac5746a2c9
|
@ -0,0 +1,56 @@
|
|||
import sys
|
||||
from grid import *
|
||||
|
||||
G = [list(l) for l in sys.stdin.read().strip().split("\n")]
|
||||
|
||||
def build_zone(G, x:int, y:int, zone:set[tuple[int,int]]):
|
||||
zone.add((x, y))
|
||||
v = get_in_grid(G, x, y)
|
||||
for dx, dy in MOVE4:
|
||||
xn = x +dx
|
||||
yn = y + dy
|
||||
if (xn, yn) not in zone:
|
||||
if get_in_grid(G, xn, yn) == v:
|
||||
build_zone(G, xn, yn, zone)
|
||||
|
||||
def perimeter(zone:set[tuple[int,int]]) -> int:
|
||||
return sum (
|
||||
(x+dx, y+dy) not in zone
|
||||
for (x,y) in zone
|
||||
for (dx, dy) in MOVE4)
|
||||
|
||||
def corners(zone:set[tuple[int,int]]) -> int:
|
||||
corners = 0
|
||||
for x,y in zone:
|
||||
# define tile neighbourhood
|
||||
[N,E,S,W] = [(x+dx,y+dy)in zone for (dx,dy) in MOVE4]
|
||||
[SE,NW,NE,SW] = [(x+dx,y+dy)in zone for (dx,dy) in DIAG4]
|
||||
# alone == no adjacent
|
||||
if not (W or N or E or S): corners+=4
|
||||
# touches zone on just 1 side
|
||||
if (W+N+E+S==1): corners+=2
|
||||
# outside corners
|
||||
if (S and E and not N and not W): corners+=1
|
||||
if (S and W and not N and not E): corners+=1
|
||||
if (N and E and not S and not W): corners+=1
|
||||
if (N and W and not S and not E): corners+=1
|
||||
# inside corners
|
||||
if (E and N and not NE): corners+=1
|
||||
if (E and S and not SE): corners+=1
|
||||
if (W and N and not NW): corners+=1
|
||||
if (W and S and not SW): corners+=1
|
||||
return corners
|
||||
|
||||
T1 = T2 = 0
|
||||
checked = set()
|
||||
W, H = grid_geom(G)
|
||||
for y in range(W):
|
||||
for x in range(H):
|
||||
if (x,y) in checked: continue
|
||||
zone = set()
|
||||
build_zone(G, x, y, zone)
|
||||
area = len(zone)
|
||||
T1 += area * perimeter(zone)
|
||||
T2 += area * corners(zone)
|
||||
checked |= zone
|
||||
print(T1, T2)
|
Loading…
Reference in New Issue