diff --git a/2022/Cargo.toml b/2022/Cargo.toml new file mode 100644 index 0000000..e71419a --- /dev/null +++ b/2022/Cargo.toml @@ -0,0 +1,26 @@ +[package] +name = "aoc_2022" +version = "0.1.0" +edition = "2021" + +# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html + +[dependencies] +anyhow = "1.0.66" +clap = { version = "4.0.19", features = ["derive"] } +nom = "7.1.1" + +[dev-dependencies] +criterion = "0.4.0" + +[profile.release] +# Keep debug information in release for better flamegraphs +debug = true + +[profile.bench] +# And same for benchmarking +debug = true + +[[bench]] +name = "days" +harness = false diff --git a/2022/benches/days.rs b/2022/benches/days.rs new file mode 100644 index 0000000..ad42ca3 --- /dev/null +++ b/2022/benches/days.rs @@ -0,0 +1,46 @@ +use std::fs::File; +use std::io::Read; + +use aoc_2022::get_implementation; +use criterion::criterion_group; +use criterion::criterion_main; +use criterion::BenchmarkId; +use criterion::Criterion; + +/// Number of days we have an implementation to benchmark +const DAYS_IMPLEMENTED: u8 = 0; + +fn read_input(day: u8) -> Vec { + let input_path = format!("inputs/{:02}.txt", day); + + let mut buffer = Vec::new(); + File::open(input_path) + .expect("Failed to open input file") + .read_to_end(&mut buffer) + .expect("Failed to read input file"); + + buffer +} + +pub fn benchmark_days(c: &mut Criterion) { + for day in 1..=DAYS_IMPLEMENTED { + let input = read_input(day); + + let part1 = get_implementation(day, false).unwrap(); + + c.bench_with_input(BenchmarkId::new("part1", day), &input, |b, i| { + b.iter(|| part1(i)); + }); + + if day < 25 { + let part2 = get_implementation(day, true).unwrap(); + + c.bench_with_input(BenchmarkId::new("part2", day), &input, |b, i| { + b.iter(|| part2(i)); + }); + } + } +} + +criterion_group!(benches, benchmark_days); +criterion_main!(benches); diff --git a/2022/inputs/.gitkeep b/2022/inputs/.gitkeep new file mode 100644 index 0000000..e69de29 diff --git a/2022/src/day01.rs b/2022/src/day01.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day01.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day02.rs b/2022/src/day02.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day02.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day03.rs b/2022/src/day03.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day03.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day04.rs b/2022/src/day04.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day04.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day05.rs b/2022/src/day05.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day05.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day06.rs b/2022/src/day06.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day06.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day07.rs b/2022/src/day07.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day07.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day08.rs b/2022/src/day08.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day08.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day09.rs b/2022/src/day09.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day09.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day10.rs b/2022/src/day10.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day10.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day11.rs b/2022/src/day11.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day11.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day12.rs b/2022/src/day12.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day12.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day13.rs b/2022/src/day13.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day13.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day14.rs b/2022/src/day14.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day14.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day15.rs b/2022/src/day15.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day15.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day16.rs b/2022/src/day16.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day16.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day17.rs b/2022/src/day17.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day17.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day18.rs b/2022/src/day18.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day18.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day19.rs b/2022/src/day19.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day19.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day20.rs b/2022/src/day20.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day20.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day21.rs b/2022/src/day21.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day21.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day22.rs b/2022/src/day22.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day22.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day23.rs b/2022/src/day23.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day23.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day24.rs b/2022/src/day24.rs new file mode 100644 index 0000000..745aff3 --- /dev/null +++ b/2022/src/day24.rs @@ -0,0 +1,9 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} + +pub fn part2(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/day25.rs b/2022/src/day25.rs new file mode 100644 index 0000000..2bc42ed --- /dev/null +++ b/2022/src/day25.rs @@ -0,0 +1,5 @@ +use anyhow::Result; + +pub fn part1(_input: &[u8]) -> Result { + todo!() +} diff --git a/2022/src/lib.rs b/2022/src/lib.rs new file mode 100644 index 0000000..c659099 --- /dev/null +++ b/2022/src/lib.rs @@ -0,0 +1,90 @@ +use anyhow::Result; + +mod day01; +mod day02; +mod day03; +mod day04; +mod day05; +mod day06; +mod day07; +mod day08; +mod day09; +mod day10; +mod day11; +mod day12; +mod day13; +mod day14; +mod day15; +mod day16; +mod day17; +mod day18; +mod day19; +mod day20; +mod day21; +mod day22; +mod day23; +mod day24; +mod day25; + +type Solution = fn(&[u8]) -> Result; + +pub fn get_implementation(day: u8, part2: bool) -> Result { + if !part2 { + match day { + 1 => Ok(day01::part1), + 2 => Ok(day02::part1), + 3 => Ok(day03::part1), + 4 => Ok(day04::part1), + 5 => Ok(day05::part1), + 6 => Ok(day06::part1), + 7 => Ok(day07::part1), + 8 => Ok(day08::part1), + 9 => Ok(day09::part1), + 10 => Ok(day10::part1), + 11 => Ok(day11::part1), + 12 => Ok(day12::part1), + 13 => Ok(day13::part1), + 14 => Ok(day14::part1), + 15 => Ok(day15::part1), + 16 => Ok(day16::part1), + 17 => Ok(day17::part1), + 18 => Ok(day18::part1), + 19 => Ok(day19::part1), + 20 => Ok(day20::part1), + 21 => Ok(day21::part1), + 22 => Ok(day22::part1), + 23 => Ok(day23::part1), + 24 => Ok(day24::part1), + 25 => Ok(day25::part1), + _ => anyhow::bail!("Invalid day for part 1: {day}"), + } + } else { + match day { + 1 => Ok(day01::part2), + 2 => Ok(day02::part2), + 3 => Ok(day03::part2), + 4 => Ok(day04::part2), + 5 => Ok(day05::part2), + 6 => Ok(day06::part2), + 7 => Ok(day07::part2), + 8 => Ok(day08::part2), + 9 => Ok(day09::part2), + 10 => Ok(day10::part2), + 11 => Ok(day11::part2), + 12 => Ok(day12::part2), + 13 => Ok(day13::part2), + 14 => Ok(day14::part2), + 15 => Ok(day15::part2), + 16 => Ok(day16::part2), + 17 => Ok(day17::part2), + 18 => Ok(day18::part2), + 19 => Ok(day19::part2), + 20 => Ok(day20::part2), + 21 => Ok(day21::part2), + 22 => Ok(day22::part2), + 23 => Ok(day23::part2), + 24 => Ok(day24::part2), + _ => anyhow::bail!("Invalid day for part 2: {day}"), + } + } +} diff --git a/2022/src/main.rs b/2022/src/main.rs new file mode 100644 index 0000000..86dc88e --- /dev/null +++ b/2022/src/main.rs @@ -0,0 +1,61 @@ +use std::fs::File; +use std::io::Read; +use std::num::NonZeroU8; +use std::path::PathBuf; +use std::time::Instant; + +use anyhow::Result; +use clap::Parser; + +use aoc_2022::get_implementation; + +/// Advent of Code 2021 runner +#[derive(Parser)] +struct Opts { + /// Which day to run + day: NonZeroU8, + + /// Print time taken + #[clap(short, long)] + time: bool, + + /// Run part 2 instead of part 1 + #[clap(short = '2', long)] + part2: bool, + + /// Read input from the given file instead of stdin + #[clap(short, long)] + input: Option, +} + +impl Opts { + fn input_data(&self) -> Result> { + let mut buffer = Vec::new(); + + if let Some(input) = &self.input { + File::open(input)?.read_to_end(&mut buffer)?; + } else { + std::io::stdin().read_to_end(&mut buffer)?; + } + + Ok(buffer) + } +} + +fn main() -> Result<()> { + let opts: Opts = Opts::parse(); + + let input = opts.input_data()?; + + let implementation = get_implementation(opts.day.get(), opts.part2)?; + + let begin = Instant::now(); + let result = implementation(&input)?; + + if opts.time { + eprintln!("Execution time: {:?}", Instant::now().duration_since(begin)); + } + + println!("{}", result); + Ok(()) +} diff --git a/2022/src/samples/.gitkeep b/2022/src/samples/.gitkeep new file mode 100644 index 0000000..e69de29