1use crate::util::intcode::*;
7use crate::util::parse::*;
8
9type Input = (i64, i64);
10
11pub fn parse(input: &str) -> Input {
12 let code: Vec<_> = input.iter_signed().collect();
13 let mut network: Vec<_> = (0..50)
14 .map(|address| {
15 let mut computer = Computer::new(&code);
16 computer.input(address);
17 computer
18 })
19 .collect();
20
21 let mut nat_x = 0;
22 let mut nat_y = 0;
23 let mut first_y = None;
24 let mut idle_y = None;
25
26 loop {
27 let mut empty = 0;
28
29 for index in 0..50 {
30 let computer = &mut network[index];
31
32 match computer.run() {
33 State::Output(address) => {
34 let State::Output(x) = computer.run() else { unreachable!() };
36 let State::Output(y) = computer.run() else { unreachable!() };
37
38 if address == 255 {
39 first_y.get_or_insert(y);
41 nat_x = x;
42 nat_y = y;
43 } else {
44 let destination = &mut network[address as usize];
45 destination.input(x);
46 destination.input(y);
47 }
48 }
49 State::Input => {
51 empty += 1;
52 computer.input(-1);
53 }
54 State::Halted => unreachable!(),
55 }
56 }
57
58 if empty == 50 {
59 if idle_y == Some(nat_y) {
60 break;
61 }
62 idle_y = Some(nat_y);
63
64 let destination = &mut network[0];
65 destination.input(nat_x);
66 destination.input(nat_y);
67 }
68 }
69
70 (first_y.unwrap(), idle_y.unwrap())
71}
72
73pub fn part1(input: &Input) -> i64 {
74 input.0
75}
76
77pub fn part2(input: &Input) -> i64 {
78 input.1
79}