diff options
| author | Reiner Herrmann <reiner@reiner-h.de> | 2022-12-28 17:33:24 +0100 |
|---|---|---|
| committer | Reiner Herrmann <reiner@reiner-h.de> | 2022-12-28 17:33:24 +0100 |
| commit | 32e3312e273082ba8a7f8455bbffa7a48c94f0b1 (patch) | |
| tree | 1058f028700d03b0a0a94f2096bb0079f4613a85 | |
| parent | 93e5164ede6a05f9172fd6bcc4f85fbd1fd6bcaa (diff) | |
day24
| -rw-r--r-- | inputs/day24 | 27 | ||||
| -rw-r--r-- | src/bin/day24.rs | 161 |
2 files changed, 188 insertions, 0 deletions
diff --git a/inputs/day24 b/inputs/day24 new file mode 100644 index 0000000..d66380d --- /dev/null +++ b/inputs/day24 @@ -0,0 +1,27 @@ +#.######################################################################################################################## +#.v^<>^^.<^^<v>v>>>.<^<<v.^>vv>>^<<<v>.v<^v^<v<<^<^^<^<^v><^vv.v^^.>^><vv><^<.<^v<>.v<v..^>><v>.vvv.v>^^<^>.<<^<^<^>v.^^<# +#.^^<v>><<v><vv<>..<>v<^v><<>><>v.>v.^^<<.v.^<^<vv><v<<v><<^<>^v>v>><>v..v^<^.v><>^>><v<<>v^<<v<v>v.v<v>><<v>^v<v^...<<<># +#><vv>>v>v<^>^^^^vv^<v^<<v<>^<^.^^>^<^vv>^v>><<^^<.>^>v<^v<.v.^<^^v.<.>.<^>v^>.v>>^vv^v.>>>v<<<<v.^^v<^^<^><<<<.^>.>vvv>># +#<.vv>.><<.<^v.>v^v>><v>><<^vv>^v^>.><v>>><^><v<v^^vv>.v^^<v>vv<>v>^v.>>v^>..v<>^v.^>><.vv><^...<>^^>v>vvv>^<^<><v>v<^^^<# +#>^.^>vvv>vv>^^vv>v^^v>vv>v^v>^<v>>vvvv^>.v^<v^><^>vvv<>vv<^v<.<^v^>^vv^<><>.^.^>><<^^>^<v^>>>>v><<v^^>^^>>v^v.<^vv^<^v<># +#><^>><vv^vvv.v><v<>^v>^<<<^^<><^<<v<>^<<v><<<v>><v<^^<vv<.>^v>^<v>.>v>>^^>^>><>.<<v<^><>>>^.<vv>.^^<.^^>>v.><<v<>><>v^><# +#>>^.<<v.^v>^^v.>v.vv^<<.v<v<..<<v^^>^v.><>v<^^<<.>v>v>v>^v>.<>v<><<^v><^>><^v>v^v>^vvv>>>..>^>>.><v><>.^^v.><<vv<.v>^^<.# +#>vv>^^.<>^v<^<<v^>v<^^v><>>>>v^vv>v<^v^><><^.<v^>.<^.v^>><vv>>vvv>^v<<<><vv<v^<<>v>>^v>^^^>^v><^^>^^^<<^^<v<<v<v>^^^<^>># +#>.v^<<.vv<^v>^>>v<>v^v^^v^v<^^<<..<<^v<<<<^<v>^>.<>v<v<v<.<.v>vv^>><^.<.v<^<^v><v<v>.v.><<^>>v^.^vv.vv^.>^^>vv<>^..v>^v<# +#..v.>^><<>..<>.<^<<v>^^^^><<><<vv><^>v>^v<vv>v><vv.^<.<<<<v^v<>^^^vv>.>>>v^v<v<^.<v<<^.v<><<>>v<<<.>>v.^^>^^.>.<.>vv>^>># +#>^^vv<<><<v<^.v>>v>^^^v^<v.^><<<<<v^v>v<<^v..^<.vv.^v>vvv>^v<..v<><<^<<vv<>>>>^>^^<>^<^<^^.vv>>^>^>^v^>.<^.<<.>v^>vv<.^<# +#<v^vv>^^v>vv>^.^>v>v^v>vv.>>.>v^v^>.^v<^.>^<<<v.>^>^^<>vv<.<^^<^v<^><v^v^.^<><v^^v^>.<vv^>v^v<v^><>^<vv>v<><^v<v.<<^.>^># +#<>^<^<v><^^.^^>..^^>v>>>>^v<.<>>.<^v^>vvvvv>^<<.><^<v<.v<^><^^>vv<^<^<>v>v<>^^v>>^^>>v<^^<v>v^^^vvv<<<<<>>>v>^v.<^^>^>^<# +#>.<^v<.<^v.v>^.>>><^<<^^<<.<>><>>>^vvv<v<v<<^^vv<<<^v^v^vv<^v>>^^vv.^>^.v^^^>>v^>.<>.^^>v^^^^><^^>^>>.v<v^<^>^v^>^<<<v<<# +#>><><.>v^<>^^>.^>^v>^.^<v><><>.<v<^v>>>>v.<>>.^vv>v.vv.><vv^v>^<>>v>vv.v>v>v<><>>>^..^v>^^><..^..^..^vvv>><>v<>v<^<<>v<<# +#<vv^vvv><>v^v.<^v^^v<.<>v<>.^v^<<^<><.^vv<>^>>.v<<><vv<^^<>>v^.^v><v^^<>v.v<.>^^v^<<<^^<<v<^^^<<<<>^^v>><><<><>v>v<v.>^># +#.<.^>^>^>^v..v>^.<v<^<<<^vvv>vv><^^v^<.>>.^<.^^<<>>^><<>>^^.^<<^^><^v<.><>.<<<.vvv>>vv^v<^v<>vv<<^v^^<v.v^<<^>v^>v<><vv<# +#.vvvv>>^>^<..^>>^>vv^.^>^<<v>^^v>v>^<>.>vv<v^>>>^.^<<^>>^>^>vvv><vv^^<^.^^.<^^v.<v<>^<<<v^>><<.^^^^>^>>>v<<>>v>v<>v<v><.# +#<<vv.<v>^^v<.>>^>^<>^><.<v^><>>.^<v^v<<.v>>.<>.v>^>^v><><^<><<<v^<><<v^..^v^v>^.><>>>v^.^>vv<<^>v<><.^^v<>vv>v^v<><^>>><# +#><>^v>v<>><vv>>v<>^<v>v^^>^v^>^^<v>v>^^v><<^v>>vv<^><>^>^^>>v^^<^<v>.^>v^vv^<.v>^v^.v^><><>>v.v^vv^<v>^>^><v>^>^>v>^v..<# +#>v<^^<^>.<>v<v<.^vv^>>v><^^v<^^>>^>^<^^>>>^<v<^v<>v<^>v>^>v^v>^.<<v^>vv<^<.><^><<^>v><^<v>^<^v>v^>><^vvv^>>v>>vv>v^>^><<# +#<vvv<><^.>v.^><v<^^<v><^<vvv.^..v^>...v^><<^^><^>^^vv>^v>v^<v<<>^>^^..<^<<v><<>.><<>^vvvv>v^><.^^>>v>>>^>>^<^<^<v^>vvv>># +#><<<^^.^<.^.^^<>^.vv^^^<v^<<<vv<<>^<v<^>>v^>>v<<v^^.v^<.vv<v<><<.v><<^>>v><.v><v>v^^v^v<^><vvvvv<^.<<>v^.<>^.^><>^v><>^<# +#<.<>.>v^><<>^^<<vv>^>^v>>>v>v><^v><v.>>^<>>.<vv<<<v<v^<<vv^<.v^^>vv>>^<^<v<v<<>vv.><v..>>>.>^v<<vv><v^^^vv^^<>^>v<^^>v.># +#<>^^<>>^v>v<<>^.>>^^^<<v>^vv^<^<.<<<vv>>v>^^<^v><><>.<>.^><<^^^>^vv><>v.<>v<.<v>>><v.^>^>vv<v>^<v^<<v^v>v..>^^<^^.><>^><# +########################################################################################################################.# diff --git a/src/bin/day24.rs b/src/bin/day24.rs new file mode 100644 index 0000000..109b7b5 --- /dev/null +++ b/src/bin/day24.rs @@ -0,0 +1,161 @@ +use std::collections::{HashMap, HashSet}; + +static DAY: u8 = 24; + +fn main() { + let input = advent::read_lines(DAY); + println!("{DAY}a: {}", travel_time(&input)); + println!("{DAY}b: {}", travel_time_3(&input)); +} + +#[derive(Clone,Copy)] +enum Direction { + Up, + Down, + Left, + Right, +} + +#[derive(Clone,Copy)] +enum Object { + Wall, + Blizzard { direction: Direction }, +} + +impl Object { + fn new(input: char) -> Object { + match input { + '^' => Object::Blizzard { direction: Direction::Up }, + 'v' => Object::Blizzard { direction: Direction::Down }, + '<' => Object::Blizzard { direction: Direction::Left }, + '>' => Object::Blizzard { direction: Direction::Right }, + '#' => Object::Wall, + _ => unimplemented!(), + } + } +} + +struct Map { + map: HashMap<(isize,isize),Vec<Object>>, + dimensions: (isize, isize), + start: (isize, isize), + end: (isize, isize), +} + +impl Map { + fn new(input: &[String]) -> Map { + let mut map = HashMap::new(); + let mut dimensions = (0, 0); + let mut start = (0, 0); + let mut end = (0, 0); + for (y, line) in input.iter().enumerate() { + for (x, c) in line.chars().enumerate() { + let (x, y) = (x as isize, y as isize); + if c == '.' { + if y == 0 { + start = (x, y); + } else { + end = (x, y); + } + } else { + map.insert((x,y), vec![Object::new(c)]); + } + dimensions = (x, y); + } + } + Map { map, dimensions, start, end } + } + + fn next_map(&self) -> HashMap<(isize,isize),Vec<Object>> { + let mut new_map = HashMap::<(isize,isize),Vec<Object>>::new(); + for (&(x,y), objects) in &self.map { + for object in objects { + let new_pos = match object { + Object::Wall => (x,y), + Object::Blizzard { direction: Direction::Up } => { + if y - 1 == 0 { (x, self.dimensions.1 - 1) } else { (x, y - 1) } + }, + Object::Blizzard { direction: Direction::Down } => { + if y + 1 == self.dimensions.1 { (x, 1) } else { (x, y + 1) } + }, + Object::Blizzard { direction: Direction::Left } => { + if x - 1 == 0 { (self.dimensions.0 - 1, y) } else { (x - 1, y) } + }, + Object::Blizzard { direction: Direction::Right } => { + if x + 1 == self.dimensions.0 { (1, y) } else { (x + 1, y) } + }, + }; + new_map.entry(new_pos).or_default().push(*object); + } + } + new_map + } + + fn travel_time(&mut self) -> usize { + let mut visited = HashSet::from([self.start]); + let mut time = 0; + loop { + let next_map = self.next_map(); + let mut next_visited = HashSet::new(); + for &(x,y) in &visited { + if !next_map.contains_key(&(x,y)) { + next_visited.insert((x,y)); + } + if x < self.dimensions.0 && !next_map.contains_key(&(x+1,y)) { + next_visited.insert((x+1,y)); + } + if x > 0 && !next_map.contains_key(&(x-1,y)) { + next_visited.insert((x-1,y)); + } + if y < self.dimensions.1 && !next_map.contains_key(&(x,y+1)) { + next_visited.insert((x,y+1)); + } + if y > 0 && !next_map.contains_key(&(x,y-1)) { + next_visited.insert((x,y-1)); + } + } + visited = next_visited; + self.map = next_map; + time += 1; + if visited.contains(&self.end) { + return time; + } + } + } +} + +fn travel_time(input: &[String]) -> usize { + let mut map = Map::new(input); + map.travel_time() +} + +fn travel_time_3(input: &[String]) -> usize { + let mut map = Map::new(input); + let mut time = map.travel_time(); + (map.start, map.end) = (map.end, map.start); + time += map.travel_time(); + (map.start, map.end) = (map.end, map.start); + time += map.travel_time(); + + time +} + +#[cfg(test)] +mod tests { + use super::*; + + #[test] + fn test() { + let input = [ + "#.######", + "#>>.<^<#", + "#.<..<<#", + "#>v.><>#", + "#<^v^^>#", + "######.#", + ].iter().map(|&x| String::from(x)).collect::<Vec<_>>(); + + assert_eq!(travel_time(&input), 18); + assert_eq!(travel_time_3(&input), 54); + } +} |
