solution: day 6
This commit is contained in:
parent
50dc9543da
commit
55688a124d
@ -3,7 +3,7 @@ pub mod d2;
|
||||
pub mod d3;
|
||||
pub mod d4;
|
||||
pub mod d5;
|
||||
// pub mod d6;
|
||||
pub mod d6;
|
||||
// pub mod d7;
|
||||
// pub mod d8;
|
||||
// pub mod d9;
|
||||
|
||||
131
src/days/d6.rs
Normal file
131
src/days/d6.rs
Normal file
@ -0,0 +1,131 @@
|
||||
#![allow(non_upper_case_globals)]
|
||||
use crate::prelude::*;
|
||||
|
||||
pub type I = Vec<Vec<char>>;
|
||||
pub type O = usize;
|
||||
|
||||
fn _parse (data: &str) -> I {
|
||||
data.lines().map(|line| line.chars().collect()).collect()
|
||||
}
|
||||
|
||||
fn _traverse (data: &I) -> S<(usize, usize)> {
|
||||
let (mut sy, mut sx) = data.iter().enumerate().find_map(|(y, row)| row.iter().position(|e| *e == '^').map(|x| (y, x))).unwrap();
|
||||
|
||||
let rows = data.len();
|
||||
let cols = data[0].len();
|
||||
|
||||
let mut s: S<(usize, usize)> = S::new();
|
||||
const dirs: [(isize, isize); 4] = [(-1, 0), (0, 1), (1, 0), (0, -1)];
|
||||
let mut dir = 0;
|
||||
|
||||
loop {
|
||||
|
||||
let (dy, dx) = dirs[dir];
|
||||
let ny = sy.checked_add_signed(dy);
|
||||
let nx = sx.checked_add_signed(dx);
|
||||
|
||||
match (ny, nx) {
|
||||
(Some(ny), Some(nx)) if ny < rows && nx < cols => {
|
||||
if data[ny][nx] == '#' {
|
||||
dir = (dir + 1) % 4;
|
||||
} else {
|
||||
s.insert((ny, nx));
|
||||
sy = ny;
|
||||
sx = nx;
|
||||
}
|
||||
},
|
||||
_ => break,
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
s
|
||||
}
|
||||
|
||||
fn _silver (data: I) -> O {
|
||||
let ans = _traverse(&data);
|
||||
ans.len()
|
||||
}
|
||||
|
||||
fn _gold (mut data: I) -> O {
|
||||
let path = _traverse(&data);
|
||||
let (sy, sx) = data.iter().enumerate().find_map(|(y, row)| row.iter().position(|e| *e == '^').map(|x| (y, x))).unwrap();
|
||||
data[sy][sx] = '.';
|
||||
|
||||
let rows = data.len();
|
||||
let cols = data[0].len();
|
||||
|
||||
const dirs: [(isize, isize); 4] = [(-1, 0), (0, 1), (1, 0), (0, -1)];
|
||||
|
||||
let mut loops = 0;
|
||||
|
||||
'outer : for (cy, cx) in path {
|
||||
if cy == sy && cx == sx { continue; }
|
||||
if data[cy][cx] == '.' {
|
||||
data[cy][cx] = '#';
|
||||
|
||||
let mut y = sy;
|
||||
let mut x = sx;
|
||||
|
||||
let mut s: S<((usize, usize), usize)> = S::new();
|
||||
let mut dir = 0;
|
||||
|
||||
'inner : loop {
|
||||
let (dy, dx) = dirs[dir];
|
||||
|
||||
if s.contains(&((y, x), dir)) {
|
||||
loops += 1;
|
||||
data[cy][cx] = '.';
|
||||
continue 'outer;
|
||||
}
|
||||
s.insert(((y, x), dir));
|
||||
|
||||
let ny = y.checked_add_signed(dy);
|
||||
let nx = x.checked_add_signed(dx);
|
||||
|
||||
match (ny, nx) {
|
||||
(Some(ny), Some(nx)) if ny < rows && nx < cols => {
|
||||
if data[ny][nx] == '#' {
|
||||
dir = (dir + 1) % 4;
|
||||
} else {
|
||||
y = ny;
|
||||
x = nx;
|
||||
}
|
||||
},
|
||||
_ => break 'inner,
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
data[cy][cx] = '.';
|
||||
}
|
||||
}
|
||||
|
||||
loops
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod test {
|
||||
use super::*;
|
||||
|
||||
fn read () -> I {
|
||||
let data = inc!(6);
|
||||
_parse(data)
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn silver () {
|
||||
let data = read();
|
||||
let ans = _silver(data);
|
||||
|
||||
assert_eq!(ans, 4967)
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn gold () {
|
||||
let data = read();
|
||||
let ans = _gold(data);
|
||||
|
||||
assert_eq!(ans, 1789)
|
||||
}
|
||||
}
|
||||
Loading…
Reference in New Issue
Block a user