Skip to main content

aoc/year2019/
day11.rs

1//! # Space Police
2//!
3//! This problem is a variant of [Langton's Ant](https://en.wikipedia.org/wiki/Langton%27s_ant).
4use super::intcode::*;
5use crate::util::grid::*;
6use crate::util::hash::*;
7use crate::util::parse::*;
8use crate::util::point::*;
9
10pub fn parse(input: &str) -> Vec<i64> {
11    input.iter_signed().collect()
12}
13
14pub fn part1(input: &[i64]) -> usize {
15    paint(input, 0).len()
16}
17
18pub fn part2(input: &[i64]) -> String {
19    let hull = paint(input, 1);
20
21    // Filter only white panels.
22    let panels: Vec<_> = hull.iter().filter_map(|(&k, &v)| (v == 1).then_some(k)).collect();
23
24    // Get maximum extents.
25    let x1 = panels.iter().map(|p| p.x).min().unwrap();
26    let x2 = panels.iter().map(|p| p.x).max().unwrap();
27    let y1 = panels.iter().map(|p| p.y).min().unwrap();
28    let y2 = panels.iter().map(|p| p.y).max().unwrap();
29
30    // Convert panels to characters.
31    let width = x2 - x1 + 2; // Leave room for newline character.
32    let height = y2 - y1 + 1;
33    let mut grid = Grid::new(width, height, '.');
34
35    let offset = Point::new(x1 - 1, y1);
36    panels.iter().for_each(|&point| grid[point - offset] = '#');
37    (0..height).for_each(|y| grid[Point::new(0, y)] = '\n');
38
39    grid.bytes.iter().collect()
40}
41
42fn paint(input: &[i64], initial: i64) -> FastMap<Point, i64> {
43    let mut computer = Computer::new(input);
44    let mut position = ORIGIN;
45    let mut direction = UP;
46    let mut hull = FastMap::with_capacity(5_000);
47
48    hull.insert(position, initial);
49
50    loop {
51        let panel = hull.entry(position).or_default();
52        computer.input(*panel);
53
54        let State::Output(color) = computer.run() else { break };
55        *panel = color;
56
57        let State::Output(turn) = computer.run() else { break };
58        direction = if turn == 0 { direction.counter_clockwise() } else { direction.clockwise() };
59        position += direction;
60    }
61
62    hull
63}