solution: day 10

This commit is contained in:
YK 2024-12-11 06:45:44 +03:00
parent d84113bf2e
commit 3fd38a2393
2 changed files with 104 additions and 1 deletions

View File

@ -7,7 +7,7 @@ pub mod d6;
pub mod d7;
pub mod d8;
pub mod d9;
// pub mod d10;
pub mod d10;
// pub mod d11;
// pub mod d12;
// pub mod d13;

103
src/days/d10.rs Normal file
View File

@ -0,0 +1,103 @@
use crate::prelude::*;
pub type I1 = Vec<Vec<char>>;
pub type I2 = Vec<(usize, usize)>;
pub type O = usize;
fn _parse (data: &str) -> (I1, I2) {
data.trim().lines().enumerate().fold((vec![], vec![]), |(mut map, mut zeroes), (y, line)| {
let mut l = vec![];
for (x, c) in line.trim().chars().enumerate() {
l.push(c);
if c == '0' { zeroes.push((y, x)); }
}
map.push(l);
(map, zeroes)
})
}
fn _dfs (
pos @ (y, x): (usize, usize),
map: &[Vec<char>],
visited: &mut S<(usize, usize)>,
silver: &mut S<(usize, usize)>,
gold: &mut O,
) {
visited.insert(pos);
let current = map[y][x];
if current == '9' {
silver.insert(pos);
*gold += 1;
return;
}
let neighbors = [(-1, 0), (0, -1), (0, 1), (1, 0)].into_iter().filter_map(|(dy, dx)| match (y.checked_add_signed(dy), x.checked_add_signed(dx)) {
(Some(y), Some(x)) if y < map.len() && x < map[0].len() => Some((y, x)),
_ => None
}).filter(|&(y, x)| map[y][x] as u8 - current as u8 == 1);
let cloned = visited.clone();
for n in neighbors {
if !visited.contains(&n) {
_dfs(n, map, visited, silver, gold);
}
*visited = cloned.clone();
}
}
fn _solve ((map, zeroes): &(I1, I2)) -> (O, O) {
let (mut silver, mut gold) = (0, 0);
for &z in zeroes {
let mut _sm = S::new();
_dfs(z, &map, &mut S::new(), &mut _sm, &mut gold);
silver += _sm.len();
}
(silver, gold)
}
fn _silver (i: &(I1, I2)) -> O {
_solve(i).0
}
fn _gold (i: &(I1, I2)) -> O {
_solve(i).1
}
#[cfg(test)]
mod test {
use super::*;
fn read () -> (I1, I2) {
let data = inc!(10);
_parse(data)
}
#[test]
fn sample () {
let data = inc!("10_example");
let data = _parse(data);
assert_eq!(_silver(&data), 36);
assert_eq!(_gold(&data), 81);
}
#[test]
fn silver () {
let data = read();
let ans = _silver(&data);
assert_eq!(ans, 694)
}
#[test]
fn gold () {
let data = read();
let ans = _gold(&data);
assert_eq!(ans, 1497)
}
}