diff --git a/samples/day01.txt b/samples/day01.txt new file mode 100644 index 0000000..444e241 --- /dev/null +++ b/samples/day01.txt @@ -0,0 +1,14 @@ +1000 +2000 +3000 + +4000 + +5000 +6000 + +7000 +8000 +9000 + +10000 \ No newline at end of file diff --git a/src/bin/day01.rs b/src/bin/day01.rs new file mode 100644 index 0000000..9a2750b --- /dev/null +++ b/src/bin/day01.rs @@ -0,0 +1,88 @@ +use aoc_2022::file_to_lines; + +use tracing::*; +use tracing_subscriber::EnvFilter; + +use std::cmp::max; + +struct Accum { + max_sum: i32, + current_sum: i32, +} + +impl Accum { + fn new() -> Accum { + Accum { + max_sum: 0, + current_sum: 0, + } + } +} + +fn part_1(input: &[i32]) -> i32 { + input + .iter() + .fold(Accum::new(), |a, &x| { + if x == -1 { + Accum { + max_sum: max(a.max_sum, a.current_sum), + current_sum: 0, + } + } else { + Accum { + max_sum: a.max_sum, + current_sum: a.current_sum + x, + } + } + }) + .max_sum +} + +fn part_2(input: &[i32]) -> i32 { + let mut calories: Vec = Vec::new(); + + let last_elf = input + .iter() + .fold(Accum::new(), |a, &x| { + if x == -1 { + calories.push(a.current_sum); + Accum::new() + } else { + Accum { + max_sum: a.max_sum, + current_sum: a.current_sum + x, + } + } + }) + .current_sum; + calories.push(last_elf); + + calories.sort(); + calories.iter().rev().take(3).sum() +} + +fn main() { + tracing_subscriber::fmt() + .with_env_filter(EnvFilter::from_default_env()) + .with_target(false) + .with_file(true) + .with_line_number(true) + .without_time() + .compact() + .init(); + + let sample: Vec = file_to_lines("samples/day01.txt") + .iter() + .map(|s| if s.is_empty() { -1 } else { s.parse().unwrap() }) + .collect(); + let input: Vec = file_to_lines("inputs/day01.txt") + .iter() + .map(|s| if s.is_empty() { -1 } else { s.parse().unwrap() }) + .collect(); + + assert_eq!(part_1(&sample), 24000); + info!("Part 1: {}", part_1(&input)); + + assert_eq!(part_2(&sample), 45000); + info!("Part 2: {}", part_2(&input)); +}