This commit is contained in:
Fabian Schmidt 2024-12-11 16:19:17 +01:00
parent dd6e9dbe90
commit c46843cf5a
4 changed files with 185 additions and 0 deletions

View File

@ -0,0 +1 @@
5 62914 65 972 0 805922 6521 1639064

27
y2024/src/bin/d11.rs Normal file
View File

@ -0,0 +1,27 @@
use std::{fs, time::Instant};
use utils::time::get_elapsed_string;
use y2024::days::d11;
fn main() {
let now = Instant::now();
println!("Part 1:");
part1();
println!("Ran in {}", get_elapsed_string(now.elapsed()));
let now = Instant::now();
println!("Part 2:");
part2();
println!("Ran in {}", get_elapsed_string(now.elapsed()));
}
fn part1() {
let root = env!("CARGO_MANIFEST_DIR");
let content = fs::read_to_string(format!("{root}/resources/11_input.txt")).unwrap();
println!("{}", d11::process_part1(&content));
}
fn part2() {
let root = env!("CARGO_MANIFEST_DIR");
let content = fs::read_to_string(format!("{root}/resources/11_input.txt")).unwrap();
println!("{}", d11::process_part2(&content, 75));
}

155
y2024/src/days/d11.rs Normal file
View File

@ -0,0 +1,155 @@
use std::collections::HashMap;
use itertools::Itertools;
pub fn process_part1(input: &str) -> u64 {
let stones = input
.split_whitespace()
.map(|stone| stone.parse::<u64>().unwrap())
.collect_vec();
let mut result = stones;
for _ in 0..25 {
result = blink(result);
}
let mut test = HashMap::new();
for stone in result.iter() {
test.entry(stone)
.and_modify(|count| *count += 1)
.or_insert(1);
}
result.len() as u64
}
pub fn process_part2(input: &str, blinks: u64) -> u64 {
let mut stones: HashMap<u64, u64> = HashMap::new();
input.split_whitespace().for_each(|stone| {
let stone = stone.parse::<u64>().unwrap();
stones
.entry(stone)
.and_modify(|count| *count += 1)
.or_insert(1);
});
let mut stones_after: HashMap<u64, u64> = HashMap::new();
for _idx in 0..blinks {
for (stone, count) in stones.iter() {
if *stone == 0 {
stones_after
.entry(1)
.and_modify(|inner_count| *inner_count += count)
.or_insert(*count);
} else if (((*stone as f64).log10() + 1.0).floor() as u64) % 2 == 0 {
let num_digits = ((*stone as f64).log10() + 1.0).floor() as u64;
let digits_per_side = num_digits / 2;
let left = stone / 10_u64.pow(digits_per_side as u32);
let right = stone % 10_u64.pow(digits_per_side as u32);
stones_after
.entry(left)
.and_modify(|inner_count| *inner_count += count)
.or_insert(*count);
stones_after
.entry(right)
.and_modify(|inner_count| *inner_count += count)
.or_insert(*count);
//stones_after.push(left);
//stones_after.push(right);
} else {
let new_stone = stone * 2024;
stones_after
.entry(new_stone)
.and_modify(|inner_count| *inner_count += count)
.or_insert(*count);
//stones_after.push(stone * 2024);
}
}
stones = stones_after.clone();
stones_after.clear();
}
stones
.into_values()
.reduce(|acc, count| acc + count)
.unwrap()
}
fn blink(stones: Vec<u64>) -> Vec<u64> {
let mut stones_after = Vec::new();
for stone in stones {
if stone == 0 {
stones_after.push(1);
continue;
}
let num_digits = ((stone as f64).log10() + 1.0).floor() as u64;
if num_digits % 2 == 0 {
let digits_per_side = num_digits / 2;
let left = stone / 10_u64.pow(digits_per_side as u32);
let right = stone % 10_u64.pow(digits_per_side as u32);
stones_after.push(left);
stones_after.push(right);
} else {
stones_after.push(stone * 2024);
}
}
stones_after
}
#[cfg(test)]
mod tests {
use itertools::Itertools;
use super::*;
const INPUT_1: &str = "0 1 10 99 999";
const INPUT_2: &str = "125 17";
#[test]
fn test_blink_1() {
let stones = INPUT_1
.split_whitespace()
.map(|stone| stone.parse::<u64>().unwrap())
.collect_vec();
let stones = blink(stones);
assert_eq!(stones, vec![1, 2024, 1, 0, 9, 9, 2021976]);
}
#[test]
fn test_blink_2() {
let stones = INPUT_2
.split_whitespace()
.map(|stone| stone.parse::<u64>().unwrap())
.collect_vec();
let mut result = stones;
for _ in 0..6 {
result = blink(result);
}
assert_eq!(
result,
vec![
2097446912, 14168, 4048, 2, 0, 2, 4, 40, 48, 2024, 40, 48, 80, 96, 2, 8, 6, 7, 6,
0, 3, 2
]
);
}
#[test]
fn part1() {
let result = process_part1(INPUT_2);
assert_eq!(result, 55312);
}
#[test]
fn part2_1() {
let result = process_part2(INPUT_1, 1);
assert_eq!(result, 7);
}
#[test]
fn part2_2() {
let result = process_part2(INPUT_2, 6);
assert_eq!(result, 22);
}
#[test]
fn part2_3() {
let result = process_part2(INPUT_2, 25);
assert_eq!(result, 55312);
}
}

View File

@ -9,3 +9,5 @@ pub mod d8;
pub mod d9; pub mod d9;
pub mod d10; pub mod d10;
pub mod d11;