day_7: done for small numbers

This commit is contained in:
2024-12-10 01:38:32 +01:00
parent e63ce3640f
commit 68c87c2b94
8 changed files with 146 additions and 11 deletions

7
Cargo.lock generated
View File

@@ -6,6 +6,7 @@ version = 3
name = "advent-of-code-2024"
version = "0.1.0"
dependencies = [
"primes",
"regex",
]
@@ -24,6 +25,12 @@ version = "2.7.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "78ca9ab1a0babb1e7d5695e3530886289c18cf2f87ec19a575a0abdce112e3a3"
[[package]]
name = "primes"
version = "0.4.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0466ef49edd4a5a4bc9d62804a34e89366810bd8bfc3ed537101e3d099f245c5"
[[package]]
name = "regex"
version = "1.11.1"

View File

@@ -4,4 +4,5 @@ version = "0.1.0"
edition = "2021"
[dependencies]
primes = "0.4.0"
regex = "1.11.1"

View File

@@ -9,7 +9,7 @@ https://adventofcode.com/2024
| 04 | Ceres Search | :pushpin: | :pushpin: | Matrix multidirectional search |
| 05 | Print Queue | :pushpin: | :pushpin: | Queue order |
| 06 | Guard Gallivant | :pushpin: | :pushpin: | 2D navigation |
| 07 | | | | |
| 07 | Bridge Repair | | | Equation parsing |
| 08 | | | | |
| 09 | | | | |
| 10 | | | | |

View File

@@ -0,0 +1,9 @@
190: 10 19
3267: 81 40 27
83: 17 5
156: 15 6
7290: 6 8 6 15
161011: 16 10 13
192: 17 8 14
21037: 9 7 18 13
292: 11 6 16 20

View File

@@ -1,11 +1,12 @@
mod fri_06;
mod mon_02;
mod sun_01;
mod thu_05;
mod tue_03;
// mod fri_06;
// mod mon_02;
// mod sun_01;
// mod thu_05;
// mod tue_03;
// mod wed_04;
mod sat_07;
mod types;
mod utils;
mod wed_04;
use types::*;
@@ -50,8 +51,12 @@ pub fn historian_hysteria() {
// println!("The fixed update mid-queue-sum is {}", fixed_queue_mid_sum);
// Friday 06
let (guard_position_count, loop_obstacle_count) =
fri_06::guard_gallivant("./assets/day_6_guard_map_input");
println!("The guard will visit {} positions", guard_position_count);
println!("The guard would loop on {} positions", loop_obstacle_count);
// let (guard_position_count, loop_obstacle_count) =
// fri_06::guard_gallivant("./assets/day_6_guard_map_input");
// println!("The guard will visit {} positions", guard_position_count);
// println!("The guard would loop on {} positions", loop_obstacle_count);
// Saturday 07
let calibration_result = sat_07::bridge_repair("./assets/day_7_calibrations_input");
println!("The total calibration result is {}", calibration_result);
}

View File

@@ -0,0 +1,83 @@
use primes::{PrimeSet, Sieve};
use super::*;
pub fn bridge_repair(input: &str) -> CalibrationResult {
let equation_vec = utils::read_calibration_equations(input);
let mut sum_result: CalibrationResult = 0;
for equation in equation_vec {
if is_equation_true(&equation) {
sum_result += equation.0;
}
}
sum_result
}
pub fn is_equation_true(equation: &Calibration) -> bool {
let operation_variants = generate_operation_variants(equation.1.len() as u32 - 1);
for variant in operation_variants {
let mut local_operands = equation.1.clone();
local_operands.reverse();
let result = calc_operation(local_operands, variant);
if result == equation.0 {
return true;
}
}
false
}
// FIXME: this goes wrong on large numbers
pub fn generate_operation_variants(count: u32) -> Vec<Vec<Operation>> {
let mut variant_list: Vec<Vec<Operation>> = vec![];
let mut pset = Sieve::new(); // get prime numbers
let variant_num = 2i32.pow(count);
for variant_index in 0..variant_num {
let mut new_vec: Vec<Operation> = vec![];
for new_operand_index in 0..count {
match variant_index as u64 % pset.get(new_operand_index as usize) {
0 => new_vec.push(Operation::MUL),
_ => new_vec.push(Operation::SUM),
}
}
variant_list.push(new_vec);
}
variant_list
}
pub fn calc_operation(
operands: CalibrationEquation,
operators: Vec<Operation>,
) -> CalibrationResult {
if operands.len() == 2 {
return operate(&operands[0], &operands[1], &operators[0]);
}
return operate(
&operands[0],
&calc_operation(operands[1..].to_vec(), operators[1..].to_vec()),
&operators[0],
);
}
pub fn operate(
first: &CalibrationResult,
second: &CalibrationResult,
operation: &Operation,
) -> CalibrationResult {
match operation {
Operation::SUM => {
return first + second;
}
Operation::MUL => {
return first * second;
}
}
}

View File

@@ -45,3 +45,14 @@ pub struct Guard {
pub y: usize,
pub dir: Direction,
}
// Bridge repair
pub type CalibrationResult = u128;
pub type CalibrationEquation = Vec<CalibrationResult>;
pub struct Calibration(pub CalibrationResult, pub CalibrationEquation);
#[derive(Debug, Clone, Copy)]
pub enum Operation {
SUM,
MUL,
}

View File

@@ -125,6 +125,25 @@ pub fn read_floor_map_and_guard_input(input: &str) -> (Guard, FloorMap) {
(the_guard, floor_map)
}
pub fn read_calibration_equations(input: &str) -> Vec<Calibration> {
let mut calibration_list: Vec<Calibration> = vec![];
for line in read_to_string(input).unwrap().lines() {
if let Some((test_value, equation_values)) = line.split_once(": ") {
let mut values: CalibrationEquation = vec![];
for equation_value in equation_values.split(" ") {
values.push(equation_value.parse::<CalibrationResult>().unwrap());
}
calibration_list.push(Calibration(
test_value.parse::<CalibrationResult>().unwrap(),
values,
));
}
}
calibration_list
}
pub fn calc_distance<T>(num_1: T, num_2: T) -> T
where
T: PartialOrd + Sub<Output = T>,