From 50dc9543da7282d2487633c9b6c21a895b309cf4 Mon Sep 17 00:00:00 2001 From: YK Date: Fri, 6 Dec 2024 10:50:50 +0300 Subject: [PATCH] solution: day 5 --- src/days.rs | 2 +- src/days/d5.rs | 108 +++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 109 insertions(+), 1 deletion(-) create mode 100644 src/days/d5.rs diff --git a/src/days.rs b/src/days.rs index 21b6c99..4436c45 100644 --- a/src/days.rs +++ b/src/days.rs @@ -2,7 +2,7 @@ pub mod d1; pub mod d2; pub mod d3; pub mod d4; -// pub mod d5; +pub mod d5; // pub mod d6; // pub mod d7; // pub mod d8; diff --git a/src/days/d5.rs b/src/days/d5.rs new file mode 100644 index 0000000..af3d9c3 --- /dev/null +++ b/src/days/d5.rs @@ -0,0 +1,108 @@ +use crate::prelude::*; + +pub type I = (M>, Vec>); +pub type O = u32; + +fn _parse (data: &str) -> I { + data.trim().split_once("\n\n").map(|(left, right)| { + let mut m: M> = M::new(); + + left.trim().lines().for_each(|line| { + let (x, y) = line.trim().split_once('|').unwrap(); + let x = p!(x); + let y = p!(y); + + m.entry(x).or_default().insert(y); + }); + + let v = right.trim().lines().map(|e| e.split(',').map(|e| p!(e)).collect()).collect(); + + (m, v) + }).unwrap() +} + + +fn _silver ((rules, list): I) -> O { + list.into_iter().filter(|page| { + let mut seen = S::new(); + + for &n in page { + let rules_for_n = rules.get(&n); + if let Some(rules) = rules_for_n { + if seen.intersection(rules).count() != 0 { + return false; + } + } + seen.insert(n); + } + true + }).map(|page| page[page.len() / 2]).sum() +} + +fn _gold ((rules, list): I) -> O { + list.into_iter().filter(|page| { + let mut seen = S::new(); + + for &n in page { + let rules_for_n = rules.get(&n); + if let Some(rules) = rules_for_n { + if seen.intersection(rules).count() != 0 { + return true; + } + } + seen.insert(n); + } + false + }) + .map(|mut page| { + let mut seen = M::new(); + let mut ptr = 0; + + 'outer : while ptr < page.len() { + let n = page[ptr]; + let rules_for_n = rules.get(&n); + if let Some(rules) = rules_for_n { + for r in rules { + if let Some(seen_idx) = seen.get(r) { + let removed = page.remove(ptr); + page.insert(*seen_idx, removed); + ptr = 0; + seen.clear(); + continue 'outer; + } + } + } + seen.insert(n, ptr); + ptr += 1; + } + + page + }) + .map(|page| page[page.len() / 2]).sum() +} + +#[cfg(test)] +mod test { + use super::*; + + fn read () -> I { + let data = inc!(5); + _parse(data) + } + + #[test] + fn silver () { + let data = read(); + let ans = _silver(data); + + assert_eq!(ans, 6260) + } + + #[test] + fn gold () { + let data = read(); + let ans = _gold(data); + + assert_eq!(ans, 5346) + } +}