2022 day 21 rust

This commit is contained in:
Maciej Jur 2022-12-21 12:01:42 +01:00
parent c35d0ddc5c
commit 0d5bb32860

View file

@ -61,13 +61,15 @@ fn chain_eval<'data, 'a>(
} }
} }
fn eval_state<'data, const SKIP_HUMAN: bool>(
fn solve1(data: &[Monkey]) -> i64 { data: &'data [Monkey]
) -> (HashMap<&'data str, i64>, HashMap<&'data str, Shout<'data>>) {
let mut finished = HashMap::new(); let mut finished = HashMap::new();
let mut awaiting = HashMap::new(); let mut awaiting = HashMap::new();
let mut dependees = HashMap::new(); let mut dependees = HashMap::new();
for monkey in data { for monkey in data {
if SKIP_HUMAN && monkey.name == "humn" { continue };
match monkey.shout { match monkey.shout {
Shout::Number(n) => { Shout::Number(n) => {
finished.insert(monkey.name, n); finished.insert(monkey.name, n);
@ -88,7 +90,12 @@ fn solve1(data: &[Monkey]) -> i64 {
}; };
} }
finished["root"] (finished, awaiting)
}
fn solve1(data: &[Monkey]) -> i64 {
eval_state::<false>(data).0["root"]
} }
fn go_back<'data, 'a>( fn go_back<'data, 'a>(
@ -127,32 +134,7 @@ fn go_back<'data, 'a>(
} }
fn solve2(data: &[Monkey]) -> i64 { fn solve2(data: &[Monkey]) -> i64 {
let mut finished = HashMap::new(); let (finished, awaiting) = eval_state::<true>(data);
let mut awaiting = HashMap::new();
let mut dependees = HashMap::new();
for monkey in data {
if monkey.name == "humn" { continue };
match monkey.shout {
Shout::Number(n) => {
finished.insert(monkey.name, n);
chain_eval(monkey.name, &dependees, &mut awaiting, &mut finished);
},
Shout::LazyOp(l, op, r) =>
match (finished.contains_key(l), finished.contains_key(r)) {
(true, true) => {
finished.insert(monkey.name, op.apply(finished[l], finished[r]));
chain_eval(monkey.name, &dependees, &mut awaiting, &mut finished);
}
_ => {
awaiting.insert(monkey.name, monkey.shout);
dependees.entry(l).or_insert(vec![]).push(monkey.name);
dependees.entry(r).or_insert(vec![]).push(monkey.name);
}
},
};
}
match awaiting["root"] { match awaiting["root"] {
Shout::LazyOp(l, _, r)=> { Shout::LazyOp(l, _, r)=> {
match (finished.get(l), finished.get(r)) { match (finished.get(l), finished.get(r)) {