class HullPaintingRobot: def __init__(self, program, input_value): self.cpu = IntCodeComputer( program, input_value=input_value, pause_on_output=True, num_output_to_capture=2, memory_size=1024, propogate_exceptions=True, ) def __repr__(self): return "<HullPaintingRobot>" def process(self): panels = defaultdict(int) panels_colored = 0 curr_position = Position(0, 0) direction = "^" while True: try: self.cpu.process() except Halt: break output = HullPaintingRobotOutput(*self.cpu.captured_output) old_color = panels[curr_position] panels[curr_position] = output.color if panels[curr_position] != old_color: panels_colored += 1 direction = direction_mapper[output.direction][direction] curr_position += advance_direction[direction] self.cpu.input_value = panels[curr_position] return panels
def test_multiple_operations(input_value, expected_output): intcode_program = ("3,21,1008,21,8,20,1005,20,22,107,8,21,20,1006,20,31," "1106,0,36,98,0,0,1002,21,125,20,4,20,1105,1,46,104," "999,1105,1,46,1101,1000,1,20,4,20,1105,1,46,98,99") cpu = IntCodeComputer(intcode_program, input_value=input_value) cpu.process() assert cpu.captured_output[0] == expected_output
def process_thru_amplification_feedback_circuit(intcode_program, phase): amplifiers = [ ("a", IntCodeComputer(intcode_program, phase=phase[0], pause_on_output=True)), ("b", IntCodeComputer(intcode_program, phase=phase[1], pause_on_output=True)), ("c", IntCodeComputer(intcode_program, phase=phase[2], pause_on_output=True)), ("d", IntCodeComputer(intcode_program, phase=phase[3], pause_on_output=True)), ("e", IntCodeComputer(intcode_program, phase=phase[4], pause_on_output=True)), ] feedback_circuit = itertools.cycle(amplifiers) input_value = 0 while True: name, amplifier = next(feedback_circuit) amplifier.input_value = input_value amplifier.process() try: input_value = amplifier.captured_output.pop() except IndexError: break return input_value
def __init__(self, program, input_value): self.cpu = IntCodeComputer( program, input_value=input_value, pause_on_output=True, num_output_to_capture=2, memory_size=1024, propogate_exceptions=True, )
def __init__(self, program: str): self.cpu = IntCodeComputer( program, pause_on_output=True, num_output_to_capture=1, memory_size=100_000, propogate_exceptions=True, ) self.program = self.cpu.program
def __init__(self, program): self.cpu = IntCodeComputer( program, input_value=JoystickDirection.LEFT, pause_on_output=True, num_output_to_capture=3, memory_size=100_000, propogate_exceptions=True, ) self.score = 0
class ArcadeCabinet: def __init__(self, program): self.cpu = IntCodeComputer( program, input_value=JoystickDirection.LEFT, pause_on_output=True, num_output_to_capture=3, memory_size=100_000, propogate_exceptions=True, ) self.score = 0 def __repr__(self): return "<ArcadeCabinet>" def insert_quarters(self): self.cpu.update_memory_address(position=0, value=2) def move_joystick(self, direction): for possible_direction in JoystickDirection: if dirrection == possible_direction: self.cpu.input_value = direction def execute(self): screen = {} ball_position = None paddle_position = None while True: try: self.cpu.process() except Halt: break output = DrawInstruction(*self.cpu.captured_output) if output.x == -1 and output.y == 0: self.score = output.tile else: screen[(output.x, output.y)] = output.tile # get position of sprites we care about if output.tile == Tile.BALL: ball_position = (output.x, output.y) elif output.tile == Tile.PADDLE: paddle_position = (output.x, output.y) # have paddle follow ball if ball_position is not None and paddle_position is not None: if ball_position[0] > paddle_position[0]: self.cpu.input_value = JoystickDirection.RIGHT elif ball_position[0] == paddle_position[0]: self.cpu.input_value = JoystickDirection.NEUTRAL elif ball_position[0] < paddle_position[0]: self.cpu.input_value = JoystickDirection.LEFT return screen
def test_update_relative_base(): relative_base = 2000 instructions = "109,19" cpu = IntCodeComputer(program=instructions, relative_base=relative_base) try: cpu.process() except Exception: assert cpu.relative_base == 2019 relative_base = cpu.relative_base
class RobotInterface: """Camera and Robot Interface Aft Scaffolding Control and Information Interface (ASCII, your puzzle input), provides access to the cameras and the vacuum robot. """ def __init__(self, program): self.cpu = IntCodeComputer(program, pause_on_output=False, memory_size=4096, propogate_exceptions=True) def run(self): """This grabs the screen output""" try: self.cpu.process() except Halt: return self.cpu.captured_output[:] raise ValueError("Unrreachable")
class RepairDroid: def __init__(self, program: str): self.cpu = IntCodeComputer( program, pause_on_output=True, num_output_to_capture=1, memory_size=100_000, propogate_exceptions=True, ) self.program = self.cpu.program def __repr__(self): return "<RepairDroid>" def map_out_floor_plan(self): floor_plan = {} frontier = deque() initial_position = XY(0, 0) frontier.append((0, self.cpu.export_state(), initial_position)) floor_plan[initial_position] = Tile.EMPTY while frontier: num_steps, state, curr_position = frontier.popleft() self.cpu.import_state(state) for movement_command, xy_delta in move_to_xy.items(): xy_to_search = curr_position + xy_delta if xy_to_search in floor_plan: continue status_code = self._run(movement_command.value)[0] if status_code == StatusCode.WALL: floor_plan[xy_to_search] = Tile.WALL continue if status_code == StatusCode.MOVED: floor_plan[xy_to_search] = Tile.EMPTY elif status_code == StatusCode.FOUND: floor_plan[xy_to_search] = Tile.OXYGEN_SYSTEM next_state = self.cpu.export_state() frontier.append((num_steps + 1, next_state, xy_to_search)) self._run(reverse_move[movement_command]) return floor_plan def _run(self, movement_command): self.cpu.input_value = movement_command while True: try: self.cpu.process() except Halt: break return self.cpu.captured_output raise ValueError("Unreachable. Program should loop forever")
def test_jump__immediate_mode(input_value, expected_output): intcode_program = "3,3,1105,-1,9,1101,0,0,12,4,12,99,1" cpu = IntCodeComputer(intcode_program, input_value=input_value) cpu.process() assert cpu.captured_output[0] == expected_output
def test_jump__position_mode(input_value, expected_output): intcode_program = "3,12,6,12,15,1,13,14,13,4,13,99,-1,0,1,9" cpu = IntCodeComputer(intcode_program, input_value=input_value) cpu.process() assert cpu.captured_output[0] == expected_output
def test_input_less_than_8__immediate_mode(input_value, expected_output): intcode_program = "3,3,1107,-1,8,3,4,3,99" cpu = IntCodeComputer(intcode_program, input_value=input_value) cpu.process() assert cpu.captured_output[0] == expected_output
def test_input_less_than_8__position_mode(input_value, expected_output): intcode_program = "3,9,7,9,10,9,4,9,99,-1,8" cpu = IntCodeComputer(intcode_program, input_value=input_value) cpu.process() assert cpu.captured_output[0] == expected_output
def test_simple_input_output_program(): intcode_program = "3,0,4,0,99" cpu = IntCodeComputer(intcode_program, input_value=1) cpu.process() assert cpu.captured_output[0] == 1
def test_process_intcode_program(intcode_program, expected_output): cpu = IntCodeComputer(intcode_program) cpu.process() assert str(cpu) == expected_output
from utils import IntCodeComputer if __name__ == "__main__": with open("2019/data/day05_input.txt") as f: intcode_program = f.readline().strip() cpu = IntCodeComputer(intcode_program, input_value=1) cpu.process() print(cpu.captured_output) cpu = IntCodeComputer(intcode_program, input_value=5) cpu.process() print(cpu.captured_output)
def test_output_has_16_chars(): intcode_program = "1102,34915192,34915192,7,4,7,99,0" cpu = IntCodeComputer(intcode_program, memory_size=1024) cpu.process() assert len(str(cpu.captured_output[0])) == 16 def test_output_produces_middle_number(): intcode_program = "104,1125899906842624,99" cpu = IntCodeComputer(intcode_program, memory_size=1024) cpu.process() assert cpu.captured_output[0] == 1125899906842624 if __name__ == "__main__": with open("2019/data/day09_input.txt", "r") as f: intcode_program = f.readline().strip() cpu = IntCodeComputer(intcode_program, memory_size=1_000_000, input_value=1) cpu.process() print(f"Test program output: {cpu.captured_output[0]}") cpu = IntCodeComputer(intcode_program, memory_size=1_000_000, input_value=2) cpu.process() print(f"Boost program output: {cpu.captured_output[0]}")
def __init__(self, program): self.cpu = IntCodeComputer(program, pause_on_output=False, memory_size=4096, propogate_exceptions=True)
def test_output_has_16_chars(): intcode_program = "1102,34915192,34915192,7,4,7,99,0" cpu = IntCodeComputer(intcode_program, memory_size=1024) cpu.process() assert len(str(cpu.captured_output[0])) == 16
def process_thru_amplification_circuit(intcode_program, phase): amplifier_a = IntCodeComputer(intcode_program, input_value=0, phase=phase[0]) amplifier_a.process() output_a = amplifier_a.captured_output[-1] amplifier_b = IntCodeComputer(intcode_program, input_value=output_a, phase=phase[1]) amplifier_b.process() output_b = amplifier_b.captured_output[-1] amplifier_c = IntCodeComputer(intcode_program, input_value=output_b, phase=phase[2]) amplifier_c.process() output_c = amplifier_c.captured_output[-1] amplifier_d = IntCodeComputer(intcode_program, input_value=output_c, phase=phase[3]) amplifier_d.process() output_d = amplifier_d.captured_output[-1] amplifier_e = IntCodeComputer(intcode_program, input_value=output_d, phase=phase[4]) amplifier_e.process() output_e = amplifier_e.captured_output[-1] return output_e
def test_output_produces_middle_number(): intcode_program = "104,1125899906842624,99" cpu = IntCodeComputer(intcode_program, memory_size=1024) cpu.process() assert cpu.captured_output[0] == 1125899906842624
def test_process_copy_of_itself(): intcode_program = "109,1,204,-1,1001,100,1,100,1008,100,16,101,1006,101,0,99" cpu = IntCodeComputer(intcode_program, memory_size=1024) cpu.process() assert str(cpu) == intcode_program
def test_multiple_inputs(intcode_program, phase, expected_output): amplifier_a = IntCodeComputer(intcode_program, input_value=0, phase=phase[0]) amplifier_a.process() output_a = amplifier_a.captured_output[-1] amplifier_b = IntCodeComputer(intcode_program, input_value=output_a, phase=phase[1]) amplifier_b.process() output_b = amplifier_b.captured_output[-1] amplifier_c = IntCodeComputer(intcode_program, input_value=output_b, phase=phase[2]) amplifier_c.process() output_c = amplifier_c.captured_output[-1] amplifier_d = IntCodeComputer(intcode_program, input_value=output_c, phase=phase[3]) amplifier_d.process() output_d = amplifier_d.captured_output[-1] amplifier_e = IntCodeComputer(intcode_program, input_value=output_d, phase=phase[4]) amplifier_e.process() output_e = amplifier_e.captured_output[-1] assert output_e == expected_output