Add solution for 2022 day 12
This commit is contained in:
parent
273a54b4ca
commit
c48a7913f5
46
2022/Cargo.lock
generated
46
2022/Cargo.lock
generated
@ -55,12 +55,48 @@ dependencies = [
|
|||||||
"itertools",
|
"itertools",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "aoc-2022-12"
|
||||||
|
version = "0.1.0"
|
||||||
|
dependencies = [
|
||||||
|
"itertools",
|
||||||
|
"petgraph",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "autocfg"
|
||||||
|
version = "1.1.0"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "either"
|
name = "either"
|
||||||
version = "1.8.0"
|
version = "1.8.0"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "90e5c1c8368803113bf0c9584fc495a58b86dc8a29edbf8fe877d21d9507e797"
|
checksum = "90e5c1c8368803113bf0c9584fc495a58b86dc8a29edbf8fe877d21d9507e797"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "fixedbitset"
|
||||||
|
version = "0.4.2"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "0ce7134b9999ecaf8bcd65542e436736ef32ddca1b3e06094cb6ec5755203b80"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "hashbrown"
|
||||||
|
version = "0.12.3"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "8a9ee70c43aaf417c914396645a0fa852624801b24ebb7ae78fe8272889ac888"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "indexmap"
|
||||||
|
version = "1.9.2"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "1885e79c1fc4b10f0e172c475f458b7f7b93061064d98c3293e98c5ba0c8b399"
|
||||||
|
dependencies = [
|
||||||
|
"autocfg",
|
||||||
|
"hashbrown",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "itertools"
|
name = "itertools"
|
||||||
version = "0.10.5"
|
version = "0.10.5"
|
||||||
@ -69,3 +105,13 @@ checksum = "b0fd2260e829bddf4cb6ea802289de2f86d6a7a690192fbe91b3f46e0f2c8473"
|
|||||||
dependencies = [
|
dependencies = [
|
||||||
"either",
|
"either",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "petgraph"
|
||||||
|
version = "0.6.2"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "e6d5014253a1331579ce62aa67443b4a658c5e7dd03d4bc6d302b94474888143"
|
||||||
|
dependencies = [
|
||||||
|
"fixedbitset",
|
||||||
|
"indexmap",
|
||||||
|
]
|
||||||
|
@ -11,6 +11,7 @@ members = [
|
|||||||
"./day-09",
|
"./day-09",
|
||||||
"./day-10",
|
"./day-10",
|
||||||
"./day-11",
|
"./day-11",
|
||||||
|
"./day-12",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
|
@ -15,7 +15,7 @@
|
|||||||
| [09] | ✓ | ✓ | [Rust] |
|
| [09] | ✓ | ✓ | [Rust] |
|
||||||
| [10] | ✓ | ✓ | [Rust] |
|
| [10] | ✓ | ✓ | [Rust] |
|
||||||
| [11] | ✓ | | [Rust] |
|
| [11] | ✓ | | [Rust] |
|
||||||
| [12] | | | |
|
| [12] | ✓ | ✓ | [Rust] |
|
||||||
| [13] | | | |
|
| [13] | | | |
|
||||||
| [14] | | | |
|
| [14] | | | |
|
||||||
| [15] | | | |
|
| [15] | | | |
|
||||||
|
14
2022/day-12/Cargo.toml
Normal file
14
2022/day-12/Cargo.toml
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
[package]
|
||||||
|
name = "aoc-2022-12"
|
||||||
|
version = "0.1.0"
|
||||||
|
edition = "2021"
|
||||||
|
|
||||||
|
|
||||||
|
[lib]
|
||||||
|
test = false
|
||||||
|
doctest = false
|
||||||
|
|
||||||
|
|
||||||
|
[dependencies]
|
||||||
|
petgraph = "0.6.2"
|
||||||
|
itertools = "0.10"
|
5
2022/day-12/Justfile
Normal file
5
2022/day-12/Justfile
Normal file
@ -0,0 +1,5 @@
|
|||||||
|
@part PART INPUT_FILE="inputs/puzzle.txt":
|
||||||
|
cargo --quiet run --bin part_{{PART}} -- {{INPUT_FILE}}
|
||||||
|
|
||||||
|
clean:
|
||||||
|
cargo clean
|
41
2022/day-12/inputs/puzzle.txt
Normal file
41
2022/day-12/inputs/puzzle.txt
Normal file
@ -0,0 +1,41 @@
|
|||||||
|
abcccccccccaaaaaaaaaaccccccccccccaaaaaaaaccaaccccccccccccccccccccccccccccccccccccccccccccaaaaaa
|
||||||
|
abccccccccccaaaaaaaaaccccccccccccaaaaaaaaaaaacccccccccccaacccacccccccccccccccccccccccccccaaaaaa
|
||||||
|
abcccccccccccaaaaaaacccccccccccccaaaaaaaaaaaaaacccccccccaaacaacccccccccaaaccccccccccccccccaaaaa
|
||||||
|
abccccccccccaaaaaaccccccccccccccaaaaaaaaaaaaaaaccccccccccaaaaaccccccccccaaacccccccccccccccccaaa
|
||||||
|
abccccccccccaaaaaaaccccccccccccaaaaaaaaaaaaaacccccccccccaaaaaacccccccccaaaacccccccccccccccccaac
|
||||||
|
abaaccaaccccaaccaaaccccccccaaaaaaaaaaaaaaacaaccccccccccaaaaaaaacccccccccaaalcccccccccccccccaaac
|
||||||
|
abaaaaaacccccccccaaccccccccaaaaaacccaaaacccaaccccccccccaaaaaaaaccccccccalllllllcccccccccccccccc
|
||||||
|
abaaaaaacccccccaaacccccccccaaaaccccccaaaccccaaaaacccccccccaacccccccaaaakllllllllcccccccaacccccc
|
||||||
|
abaaaaaacccccccaaaacccccccccaacccccccaaaccccaaaaacccccccccaacccccccaakkklllpllllccccacaaacccccc
|
||||||
|
abaaaaaaaccccccaaaaccccaaccccccccccccccccccaaaaaaccccccccccccccccccckkkkpppppplllcccaaaaaaacccc
|
||||||
|
abaaaaaaacaaaccaaaaccaaaaaaccccccccccccccccaaaaaacccccccaaaccccckkkkkkkpppppppplllcddaaaaaacccc
|
||||||
|
abcaaaacccaacccccccccaaaaaacccccaaaccccccccaaaaaacccccccaaaaccjkkkkkkkpppppuppplmmdddddaaaccccc
|
||||||
|
abccaaaaaaaaaccccccccaaaaaaccccaaaaaacccccccaaacccccccccaaaajjjkkkkkrpppuuuuupppmmmdddddacccccc
|
||||||
|
abccccaaaaaaaacccccccaaaaacccccaaaaaacccccccccccccccccccaaacjjjjrrrrrrppuuuuupqqmmmmmddddaccccc
|
||||||
|
abccccaaaaaaaaacccccccaaaacccccaaaaaaccccccccccccccccccccccjjjrrrrrrrrpuuuxuvvqqqmmmmmddddccccc
|
||||||
|
abccccaaaaaaaaacccccccccccccccccaaaaaccccaacccaccccccccaaccjjjrrrruuuuuuuxxyvvqqqqqmmmmmdddcccc
|
||||||
|
abccccaaaaaaaacccccccccaaaccccccaacaaccccaaacaacccaaacaaaccjjjrrrtuuuuuuuxxyvvvqqqqqmmmmdddcccc
|
||||||
|
abccaaaaaaaacccccccccccaaaaaccccccccccccccaaaaacccaaaaaaaccjjjrrttttxxxxxxyyvvvvvqqqqmmmmdeeccc
|
||||||
|
abccaaaccaaaccccccccaacaaaaacccccccccccccaaaaaacccaaaaaacccjjjrrtttxxxxxxxyyvvvvvvvqqqmmmeeeccc
|
||||||
|
abaaaaaaaaaacccaaaccaaaaaaaaaaaccaaaccccaaaaaaaacccaaaaaaaajjjqqrttxxxxxxxyyyyyyvvvqqqnnneeeccc
|
||||||
|
SbaaaaaaaaccccaaaaccaaaaaaaaaaaaaaaaacccaaaaaaaaccaaaaaaaaacjjjqqtttxxxxEzzyyyyvvvvqqqnnneeeccc
|
||||||
|
abcaaaaaacccccaaaaccccaaaaaaaccaaaaaaccccccaaccccaaaaaaaaaaciiiqqqtttxxxyyyyyyvvvvrrrnnneeecccc
|
||||||
|
abcaaaaaacccccaaaacccaaaaaaaaccaaaaaaccccccaaccccaaacaaacccciiiqqqqttxxyyyyyywvvvrrrnnneeeecccc
|
||||||
|
abcaaaaaaccccccccccccaaaaaaaaacaaaaacccccccccccccccccaaaccccciiiqqtttxxyyyyyywwrrrrnnnneeeccccc
|
||||||
|
abcaaacaacccccaacccccaaaaaaaaacaaaaacccccccccccccccccaaaccccciiiqqttxxxywwyyywwrrrnnnneeecccccc
|
||||||
|
abccccccccaaacaaccccccccccacccccccccccccccccccccccccccccccccciiqqqttxxwwwwwwywwrrrnnneeeccccccc
|
||||||
|
abccaacccccaaaaaccccccccccccccccccccccccccccccccccccccccaacaaiiqqqttwwwwsswwwwwrrrnnfffeccccccc
|
||||||
|
abaaaaccccccaaaaaacccccccccccccccccccccccccccccaaaccccccaaaaaiiqqqttssssssswwwwrrronfffaccccccc
|
||||||
|
abaaaaaacccaaaaaaacccccccccccccccccccccccccccaaaaaacccccaaaaaiiqqqssssssssssswrrrooofffaaaacccc
|
||||||
|
abaaaaaaccaaaaaacccccccccccccccccccccccccccccaaaaaacccccaaaaaiiqqqppssspppssssrrrooofffaaaacccc
|
||||||
|
abaaaaaaccaacaaacccccccccccccccccccccccccccccaaaaaacccccaaaaaiihpppppppppppossrrooofffaaaaacccc
|
||||||
|
abaaaaccccccccaacccccccccccccccccccccccccccccaaaaaccccccccaaahhhhppppppppppoooooooofffaaaaccccc
|
||||||
|
abaaaaccccccccccaacccccccccccccccccaaacccccccaaaaacccccccccccchhhhhhhhhhggpoooooooffffaaaaccccc
|
||||||
|
abccaacccccccacaaaccccccccccccccccaaaaacccccccccccccccccccccccchhhhhhhhhggggoooooffffaacaaacccc
|
||||||
|
abccccccccccaaaaacaaccccccccccccccaaaaaccccccccccccccccccccccccchhhhhhhhggggggggggffcaacccccccc
|
||||||
|
abccccccccccaaaaaaaaccccccccccccccaaaacccaacccccccccccaccccccccccccccaaaaaggggggggfcccccccccccc
|
||||||
|
abccccccccccccaaaaaccccaacccccccccaaaacaaaaccccccccaaaaccccccccccccccaaaacaaagggggcccccccccaccc
|
||||||
|
abcccccccccccaaaaacccccaacccccccccaaaaaaaaaccccccccaaaaaaccccccccccccaaaccaaaacccccccccccccaaac
|
||||||
|
abcccccccccccaacaaccaaaaaaaacccaaaaaaaaaaaccccccccccaaaaccccccccccccccaccccaaacccccccccccccaaaa
|
||||||
|
abccccccccccccccaaccaaaaaaaaccaaaaaaaaaaaccccccccccaaaaacccccccccccccccccccccacccccccccccccaaaa
|
||||||
|
abccccccccccccccccccccaaaaacccaaaaaaaaaaaacccccccccaacaacccccccccccccccccccccccccccccccccaaaaaa
|
5
2022/day-12/inputs/test.txt
Normal file
5
2022/day-12/inputs/test.txt
Normal file
@ -0,0 +1,5 @@
|
|||||||
|
Sabqponm
|
||||||
|
abcryxxl
|
||||||
|
accszExk
|
||||||
|
acctuvwj
|
||||||
|
abdefghi
|
41
2022/day-12/src/bin/part_one.rs
Normal file
41
2022/day-12/src/bin/part_one.rs
Normal file
@ -0,0 +1,41 @@
|
|||||||
|
use std::{env, io};
|
||||||
|
|
||||||
|
use aoc_2022_12::{parse_input, Graph};
|
||||||
|
use petgraph::algo::dijkstra;
|
||||||
|
|
||||||
|
fn main() -> io::Result<()> {
|
||||||
|
let infile_path = env::args().nth(1).expect("input file");
|
||||||
|
|
||||||
|
let result = solve(&infile_path)?;
|
||||||
|
|
||||||
|
println!("{result}");
|
||||||
|
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|
||||||
|
fn solve(path: &str) -> io::Result<i32> {
|
||||||
|
let (start, end, points) = parse_input(path)?;
|
||||||
|
|
||||||
|
let graph = Graph::from_edges(points);
|
||||||
|
|
||||||
|
let result = dijkstra(&graph, start, Some(end), |_| 1);
|
||||||
|
|
||||||
|
Ok(result[&end])
|
||||||
|
}
|
||||||
|
|
||||||
|
#[cfg(test)]
|
||||||
|
mod test {
|
||||||
|
use super::*;
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn sample() {
|
||||||
|
let result = solve("inputs/test.txt").unwrap();
|
||||||
|
assert_eq!(31, result)
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn puzzle() {
|
||||||
|
let result = solve("inputs/puzzle.txt").unwrap();
|
||||||
|
assert_eq!(420, result);
|
||||||
|
}
|
||||||
|
}
|
54
2022/day-12/src/bin/part_two.rs
Normal file
54
2022/day-12/src/bin/part_two.rs
Normal file
@ -0,0 +1,54 @@
|
|||||||
|
use std::{env, io};
|
||||||
|
|
||||||
|
use aoc_2022_12::{parse_input, Graph};
|
||||||
|
use itertools::Itertools;
|
||||||
|
use petgraph::algo::dijkstra;
|
||||||
|
|
||||||
|
fn main() -> io::Result<()> {
|
||||||
|
let infile_path = env::args().nth(1).expect("input file");
|
||||||
|
|
||||||
|
let result = solve(&infile_path)?;
|
||||||
|
|
||||||
|
println!("{result}");
|
||||||
|
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|
||||||
|
fn solve(path: &str) -> io::Result<i32> {
|
||||||
|
let (_, end, points) = parse_input(path)?;
|
||||||
|
|
||||||
|
let potential_starting_points = points
|
||||||
|
.iter()
|
||||||
|
.filter_map(|(a, _)| if a.2 == 1 { Some(*a) } else { None })
|
||||||
|
.unique()
|
||||||
|
.collect::<Vec<_>>();
|
||||||
|
|
||||||
|
let graph = Graph::from_edges(points);
|
||||||
|
let result = potential_starting_points
|
||||||
|
.into_iter()
|
||||||
|
.filter_map(|start| {
|
||||||
|
let result = dijkstra(&graph, start, Some(end), |_| 1);
|
||||||
|
result.get(&end).copied()
|
||||||
|
})
|
||||||
|
.min()
|
||||||
|
.unwrap();
|
||||||
|
|
||||||
|
Ok(result)
|
||||||
|
}
|
||||||
|
|
||||||
|
#[cfg(test)]
|
||||||
|
mod test {
|
||||||
|
use super::*;
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn sample() {
|
||||||
|
let result = solve("inputs/test.txt").unwrap();
|
||||||
|
assert_eq!(29, result)
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn puzzle() {
|
||||||
|
let result = solve("inputs/puzzle.txt").unwrap();
|
||||||
|
assert_eq!(414, result);
|
||||||
|
}
|
||||||
|
}
|
109
2022/day-12/src/lib.rs
Normal file
109
2022/day-12/src/lib.rs
Normal file
@ -0,0 +1,109 @@
|
|||||||
|
use std::{
|
||||||
|
collections::HashMap,
|
||||||
|
fs::File,
|
||||||
|
io::{self, BufRead, BufReader},
|
||||||
|
iter,
|
||||||
|
path::Path,
|
||||||
|
};
|
||||||
|
|
||||||
|
use petgraph::prelude::DiGraphMap;
|
||||||
|
|
||||||
|
pub type Graph = DiGraphMap<PointWithHeight, ()>;
|
||||||
|
type PointWithHeight = (i32, i32, i32);
|
||||||
|
|
||||||
|
pub struct HeightMap {
|
||||||
|
items: HashMap<(i32, i32), i32>,
|
||||||
|
width: i32,
|
||||||
|
height: i32,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl HeightMap {
|
||||||
|
pub fn new() -> Self {
|
||||||
|
Self {
|
||||||
|
items: HashMap::new(),
|
||||||
|
width: 0,
|
||||||
|
height: 0,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn parse_input<P>(
|
||||||
|
path: P,
|
||||||
|
) -> io::Result<(
|
||||||
|
PointWithHeight,
|
||||||
|
PointWithHeight,
|
||||||
|
Vec<(PointWithHeight, PointWithHeight)>,
|
||||||
|
)>
|
||||||
|
where
|
||||||
|
P: AsRef<Path>,
|
||||||
|
{
|
||||||
|
let file = File::open(path)?;
|
||||||
|
let mut height_map = HeightMap::new();
|
||||||
|
let mut start_point = None;
|
||||||
|
let mut end_point = None;
|
||||||
|
|
||||||
|
for (line_idx, line) in BufReader::new(file).lines().enumerate() {
|
||||||
|
let line = line?;
|
||||||
|
|
||||||
|
for (cell_idx, cell) in line.chars().enumerate() {
|
||||||
|
height_map.width = (cell_idx + 1) as i32;
|
||||||
|
|
||||||
|
let point = (line_idx as i32, cell_idx as i32);
|
||||||
|
|
||||||
|
let height = if cell == 'S' {
|
||||||
|
start_point = Some((point.0, point.1, 1));
|
||||||
|
1
|
||||||
|
} else if cell == 'E' {
|
||||||
|
end_point = Some((point.0, point.1, 26));
|
||||||
|
26
|
||||||
|
} else {
|
||||||
|
(cell as u8 - 96).into()
|
||||||
|
};
|
||||||
|
|
||||||
|
height_map.items.insert(point, height);
|
||||||
|
}
|
||||||
|
|
||||||
|
height_map.height += 1
|
||||||
|
}
|
||||||
|
|
||||||
|
let edges = build_edges(&height_map);
|
||||||
|
let start_point = start_point.expect("no start point");
|
||||||
|
let end_point = end_point.expect("no end point");
|
||||||
|
|
||||||
|
Ok((start_point, end_point, edges))
|
||||||
|
}
|
||||||
|
|
||||||
|
fn build_edges(map: &HeightMap) -> Vec<(PointWithHeight, PointWithHeight)> {
|
||||||
|
map.items
|
||||||
|
.keys()
|
||||||
|
.flat_map(|point @ (x, y)| {
|
||||||
|
let neighbors =
|
||||||
|
[(-1, 0), (0, 1), (1, 0), (0, -1)]
|
||||||
|
.iter()
|
||||||
|
.filter_map(move |(nx, ny)| {
|
||||||
|
let dx = x + nx;
|
||||||
|
let dy = y + ny;
|
||||||
|
|
||||||
|
let inside_bounds =
|
||||||
|
(0..map.height).contains(&dx) && (0..map.width).contains(&dy);
|
||||||
|
|
||||||
|
if inside_bounds {
|
||||||
|
Some((dx, dy))
|
||||||
|
} else {
|
||||||
|
None
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
iter::repeat(point).zip(neighbors).filter_map(|(a, b)| {
|
||||||
|
let height_self = map.items[&(a.0, a.1)];
|
||||||
|
let height_neighbor = map.items[&(b.0, b.1)];
|
||||||
|
|
||||||
|
if height_self + 1 >= height_neighbor {
|
||||||
|
Some(((a.0, a.1, height_self), (b.0, b.1, height_neighbor)))
|
||||||
|
} else {
|
||||||
|
None
|
||||||
|
}
|
||||||
|
})
|
||||||
|
})
|
||||||
|
.collect()
|
||||||
|
}
|
@ -9,4 +9,4 @@
|
|||||||
- [2019](2019/README.md) (0% completed)
|
- [2019](2019/README.md) (0% completed)
|
||||||
- [2020](2020/README.md) (20% completed)
|
- [2020](2020/README.md) (20% completed)
|
||||||
- [2021](2021/README.md) (68% completed)
|
- [2021](2021/README.md) (68% completed)
|
||||||
- [2022](2022/README.md) (42% completed)
|
- [2022](2022/README.md) (46% completed)
|
||||||
|
Loading…
Reference in New Issue
Block a user