Пример #1
0
from utils import get_input_lines

instr_ptr = 0
accumulator = 0
program = []

for instr, num in map(lambda x: x.split(" "), get_input_lines(__file__)):
    num = int(num)
    program.append((instr, num))

visited = set()
while True:
    if instr_ptr in visited:
        break

    visited.add(instr_ptr)

    instr, num = program[instr_ptr]
    if instr == "nop":
        instr_ptr += 1
    elif instr == "acc":
        instr_ptr += 1
        accumulator += num
    elif instr == "jmp":
        instr_ptr += num
    else:
        raise ValueError(f"Unknown instruction {instr}")

print(accumulator)
from utils import get_input_lines

pos_x = 0
pos_y = 0

waypoint_x = 10
waypoint_y = 1

for line in get_input_lines(__file__):
    action = line[0]
    n = int(line[1:])

    # Handle actions
    if action == "N":
        waypoint_y += n
    elif action == "S":
        waypoint_y -= n
    elif action == "E":
        waypoint_x += n
    elif action == "W":
        waypoint_x -= n
    elif action == "L":
        # Rotate (n//90) times CCW: (new_x, new_y) = (-old_y, old_x)
        for i in range(n // 90):
            tmp_x = waypoint_x
            waypoint_x = -waypoint_y
            waypoint_y = tmp_x
    elif action == "R":
        # Rotate (n//90) times CW: (new_x, new_y) = (old_y, -old_x)
        for i in range(n // 90):
            tmp_x = waypoint_x
Пример #3
0
from functools import reduce

from utils import get_input_lines

slopes = [(1, 1), (3, 1), (5, 1), (7, 1), (1, 2)]

tree_count = [0] * len(slopes)
x_pos = [0] * len(slopes)
line_length = 0

for line_idx, line in enumerate(get_input_lines(__file__)):
    if line_length == 0:
        line_length = len(line)

    for idx, (slope_x, slope_y) in enumerate(slopes):
        if line_idx % slope_y == 0:
            if line[x_pos[idx]] == "#":
                tree_count[idx] += 1
            x_pos[idx] = (x_pos[idx] + slope_x) % line_length

print(reduce(lambda x, y: x * y, tree_count))
from typing import Dict, Tuple

from utils import get_input_lines

grid = dict()
FLOOR = 0
FREE = 1
OCCUPIED = 2
x = 0
y = 0

for row in get_input_lines(__file__):
    x = 0
    for char in row:
        grid[(x, y)] = FLOOR if char == "." else FREE
        x += 1
    y += 1

cols = x
rows = y


def count_adjacent_occupied(x_: int, y_: int, grid_: Dict[Tuple[int, int], int]) -> int:
    count = 0
    for x_d in [-1, 0, 1]:
        for y_d in [-1, 0, 1]:
            if x_d == 0 and y_d == 0:
                # Don't count own field, only neighbours
                continue

            x_d_original = x_d
from utils import get_input_lines

active = set()

for y, line in enumerate(get_input_lines(__file__)):
    for x, char in enumerate(line):
        if char == "#":
            active.add((x, y, 0))

rounds = 6
while rounds > 0:
    rounds -= 1
    new_active = set()

    # Find minimum and maximum coordinates
    min_x, max_x = None, None
    min_y, max_y = None, None
    min_z, max_z = None, None

    for (x, y, z) in active:
        min_x = min(min_x, x) if min_x is not None else x
        max_x = max(max_x, x) if max_x is not None else x
        min_y = min(min_y, y) if min_y is not None else y
        max_y = max(max_y, y) if max_y is not None else y
        min_z = min(min_z, z) if min_z is not None else z
        max_z = max(max_z, z) if max_z is not None else z

    # Go over all cubes in the range of the active cubes
    for x in range(min_x - 1, max_x + 2):
        for y in range(min_y - 1, max_y + 2):
            for z in range(min_z - 1, max_z + 2):
from utils import get_input_lines

arrival, bus_ids = get_input_lines(__file__)
arrival = int(arrival)

smallest_bus_id = None
smallest_wait = None

for bus_id in bus_ids.split(","):
    if bus_id == "x":
        continue

    bus_id = int(bus_id)
    bus_wait = bus_id - (arrival % bus_id)

    if smallest_wait is None or bus_wait < smallest_wait:
        smallest_wait = bus_wait
        smallest_bus_id = bus_id

print(smallest_wait * smallest_bus_id)
Пример #7
0
from functools import reduce
from typing import List

from utils import get_input_lines

mods = []
rems = []

for offset, bus_id in enumerate(list(get_input_lines(__file__))[1].split(",")):
    if bus_id == "x":
        continue

    bus_id = int(bus_id)

    # Use Chinese Remainder Theorem
    # (X mod bus_id) = k * bus_id - offset, with k such that the right hand side is not negative
    rhs = bus_id - offset if offset > 0 else 0

    # Correct right hand side if it is too small
    while rhs < 0:
        rhs += bus_id

    mods.append(bus_id)
    rems.append(rhs)


def modular_inverse(a: int, b: int) -> int:
    # Source: https://en.wikipedia.org/wiki/Extended_Euclidean_algorithm#Modular_integers
    t, new_t = 0, 1
    r, new_r = b, a