Skip to main content

year2019/
day13.rs

1use crate::intcode::features::Day09Features;
2use crate::intcode::{Event, Interpreter};
3use utils::prelude::*;
4
5/// Interpreting machine code to play a brick breaker arcade game.
6#[derive(Clone, Debug)]
7pub struct Day13 {
8    interpreter: Interpreter,
9}
10
11const EMPTY: i64 = 0;
12const WALL: i64 = 1;
13const BLOCK: i64 = 2;
14const PADDLE: i64 = 3;
15const BALL: i64 = 4;
16
17impl Day13 {
18    pub fn new(input: &str, _: InputType) -> Result<Self, InputError> {
19        Ok(Self {
20            interpreter: Interpreter::parse(input, 1)?,
21        })
22    }
23
24    #[must_use]
25    pub fn part1(&self) -> u32 {
26        let mut interpreter = self.interpreter.clone();
27        let mut blocks = 0;
28
29        while interpreter.next_output::<Day09Features>().is_some() {
30            let _ = interpreter.expect_output::<Day09Features>();
31            match interpreter.expect_output::<Day09Features>() {
32                EMPTY | WALL | PADDLE | BALL => {}
33                BLOCK => blocks += 1,
34                _ => panic!("no solution found: program returned invalid tile id"),
35            }
36        }
37
38        blocks
39    }
40
41    #[must_use]
42    pub fn part2(&self) -> i64 {
43        let mut interpreter = self.interpreter.clone();
44        interpreter.mem[0] = 2;
45
46        let mut score = 0;
47        let (mut ball_x, mut paddle_x) = (0i64, 0i64);
48
49        loop {
50            let x = match interpreter.run::<Day09Features>() {
51                Event::Halt => break score,
52                Event::Input => {
53                    interpreter.push_input((ball_x - paddle_x).signum());
54                    continue;
55                }
56                Event::Output(x) => x,
57            };
58            let y = interpreter.expect_output::<Day09Features>();
59            let tile = interpreter.expect_output::<Day09Features>();
60
61            if x == -1 && y == 0 {
62                score = tile;
63                continue;
64            }
65
66            match tile {
67                EMPTY | WALL | BLOCK => {}
68                PADDLE => paddle_x = x,
69                BALL => ball_x = x,
70                _ => panic!("no solution found: program returned invalid tile id"),
71            }
72        }
73    }
74}
75
76examples!(Day13 -> (u32, i64) []);