def part1(inp: List[str]) -> Set[Coord]: h = 6 w = 50 screen = set() for line in inp: split = line.split() if split[0] == "rect": size = [int(x) for x in split[1].split('x')] for y in range(size[1]): for x in range(size[0]): screen.add(Coord(x, y)) else: if split[1] == "row": row = int(split[2].split('=')[1]) remove = set() add = set() for pix in [x for x in screen if x.y == row]: remove.add(pix) add.add(Coord((pix.x + int(split[-1]))%w, pix.y)) for r in remove: screen.remove(r) screen.update(add) else: col = int(split[2].split('=')[1]) remove = set() add = set() for pix in [x for x in screen if x.x == col]: remove.add(pix) add.add(Coord(pix.x, (pix.y + int(split[-1]))%h)) for r in remove: screen.remove(r) screen.update(add) return screen
def part1(inp: str, loc=Coord(0, 0)) -> str: print(inp, loc) move = { "U": Coord(0, -1), "D": Coord(0, 1), "L": Coord(-1, 0), "R": Coord(1, 0) } dirs = {"U": 0, "D": 1, "L": 2, "R": 3} key = inp hsh = hashlib.md5(key.encode('utf-8')).hexdigest()[0:4] valid_locs = [ Coord(x, y) for x, y in itertools.product(list(range(4)), repeat=2) ] options = set() if sum(hsh[dirs[k]] in ['b', 'c', 'd', 'e', 'f'] for k in dirs) > 0: next_locs = { loc + move[k]: k for k in move if loc + move[k] in valid_locs } else: return False if len(inp) > 600: return False if Coord(3, 3) in next_locs.keys(): return inp + next_locs[Coord(3, 3)] for next_loc in next_locs: n = part1(inp + next_locs[next_loc], next_loc) if not n: continue options.add(n) if options: return min(options, key=len) else: return False
def navigate(start: Coord, end: Coord, walls: Set[Coord], points: Dict[str, Coord]) -> int: # print("Starting pair.") loc = points[start] visited = [] end = points[end] input_commands = {'N': 1, 'S': 2, 'W': 3, 'E': 4} next_command_free = {1: 'W', 2: 'E', 3: 'S', 4: 'N'} next_command_blocked = {1: 'E', 2: 'W', 3: 'N', 4: 'S'} coord_commands = { 1: Coord(0, -1), 2: Coord(0, 1), 3: Coord(-1, 0), 4: Coord(1, 0) } last_command = input_commands['S'] while True: if loc == end: # draw(walls, visited, loc) m = len(visited) break if loc in visited: visited = visited[0:visited.index(loc)] if loc + coord_commands[last_command] in walls: last_command = input_commands[next_command_blocked[last_command]] else: visited.append(loc) loc = loc + coord_commands[last_command] last_command = input_commands[next_command_free[last_command]] next_command_blocked = {1: 'W', 2: 'E', 3: 'S', 4: 'N'} next_command_free = {1: 'E', 2: 'W', 3: 'N', 4: 'S'} last_command = input_commands['S'] visited = [] loc = points[start] while True: # draw(walls, visited, loc) if loc == end: # print(f"Pair complete.") if m < len(visited): return m else: return len(visited) if loc in visited: visited = visited[0:visited.index(loc)] if loc + coord_commands[last_command] in walls: last_command = input_commands[next_command_blocked[last_command]] else: visited.append(loc) loc = loc + coord_commands[last_command] last_command = input_commands[next_command_free[last_command]]
def __init__(self, data: str) -> None: split = data.split() loc_split = split[0].split("-") self.loc = Coord(int(loc_split[1][1:]), int(loc_split[2][1:])) self.size = int(split[1][:-1]) self.used = int(split[2][:-1]) self.free = int(split[3][:-1])
reg[loc.y][loc.x] = "O" for coord in traveled: x = coord.x y = coord.y reg[y][x] = "." # reg[39][31] = "X" # reg[4][7] = "X" for row in reg: for char in row: print(char, end='') print() if __name__ == "__main__": import os, timeit FILE_DIR = os.path.dirname(os.path.abspath(__file__)) with open(os.path.join(FILE_DIR, "day24.testinput")) as f: DATA = f.read().strip() DATA = DATA.split("\n") WALLS = set() POINTS = {} for row in range(len(DATA)): for column in range(len(DATA[row])): here = DATA[row][column] if here == "#": WALLS.add(Coord(column, row)) elif here in string.digits: POINTS[here] = Coord(column, row) print(f"Part one: {part1(WALLS, POINTS)}") # print(f"Part two: {}") # print(f"Time: {timeit.timeit('', setup='from __main__ import ', number = 1)}")
def part1(inp: int, target: Coord) -> int: steps = 0 loc = Coord(1, 1) walls = set() open_space = set() visited = [] current = Coord(0, 0) input_commands = {'N': 1, 'S': 2, 'W': 3, 'E': 4} next_command_free = {1: 'W', 2: 'E', 3: 'S', 4: 'N'} next_command_blocked = {1: 'E', 2: 'W', 3: 'N', 4: 'S'} coord_commands = { 1: Coord(0, -1), 2: Coord(0, 1), 3: Coord(-1, 0), 4: Coord(1, 0) } last_command = input_commands['S'] while True: # print(loc) if loc != current: for n in loc.neighbors(): if n not in walls and n not in open_space: x = n.x y = n.y form = (x**2) + (3 * x) + (2 * x * y) + y + (y**2) + inp if bin(form).count("1") % 2 and x >= 0 and y >= 0: walls.add(n) else: open_space.add(n) current = loc if loc in visited: visited = visited[0:visited.index(loc)] if loc + coord_commands[last_command] in walls or ( loc + coord_commands[last_command]).x < 0 or ( loc + coord_commands[last_command]).y < 0: last_command = input_commands[next_command_blocked[last_command]] else: steps += 1 visited.append(loc) loc = loc + coord_commands[last_command] last_command = input_commands[next_command_free[last_command]] if loc == target: m = len(visited) print(m) break next_command_blocked = {1: 'W', 2: 'E', 3: 'S', 4: 'N'} next_command_free = {1: 'E', 2: 'W', 3: 'N', 4: 'S'} last_command = input_commands['S'] visited = [] loc = Coord(1, 1) while True: if loc != current: for n in loc.full_neighbors(): if n not in walls and n not in open_space: x = n.x y = n.y form = (x**2) + (3 * x) + (2 * x * y) + y + (y**2) + inp if bin(form).count("1") % 2 and x >= 0 and y >= 0: walls.add(n) else: open_space.add(n) current = loc if loc in visited: visited = visited[0:visited.index(loc)] if loc + coord_commands[last_command] in walls or ( loc + coord_commands[last_command]).x < 0 or ( loc + coord_commands[last_command]).y < 0: last_command = input_commands[next_command_blocked[last_command]] else: steps += 1 visited.append(loc) loc = loc + coord_commands[last_command] last_command = input_commands[next_command_free[last_command]] if loc == target: n = len(visited) print(n) break draw(walls, visited) return min(m, n)
w -= 1 h -= 1 w = max_x for coord in walls: x = coord.x y = coord.y reg[y][x] = "#" reg[1][1] = "O" for coord in traveled: x = coord.x y = coord.y reg[y][x] = "." reg[39][31] = "X" # reg[4][7] = "X" for row in reg: for char in row: print(char, end='') print() if __name__ == "__main__": import timeit DATA = 1364 # DATA = 10 TARGET = Coord(31, 39) # TARGET = Coord(7, 4) print( f"Part one: {part1(DATA, TARGET)}" ) # not 324, too high; not 102, too high; not 84; not 88; 102-16 isn't 88 # print(f"Part two: {}") # print(f"Time: {timeit.timeit('', setup='from __main__ import ', number = 1)}")