This commit is contained in:
2024-12-08 11:40:52 +01:00
parent dbf878baf1
commit 2a91587ae5
4 changed files with 996 additions and 0 deletions

20
y2024/src/bin/d7.rs Normal file
View File

@@ -0,0 +1,20 @@
use std::fs;
use y2024::days::d7;
fn main() {
part1();
part2();
}
fn part1() {
let root = env!("CARGO_MANIFEST_DIR");
let content = fs::read_to_string(format!("{root}/resources/7_input.txt")).unwrap();
println!("{}", d7::process_part1(&content));
}
fn part2() {
let root = env!("CARGO_MANIFEST_DIR");
let content = fs::read_to_string(format!("{root}/resources/7_input.txt")).unwrap();
println!("{}", d7::process_part2(&content));
}

124
y2024/src/days/d7.rs Normal file
View File

@@ -0,0 +1,124 @@
use std::iter::zip;
pub fn process_part1(input: &str) -> i64 {
input
.lines()
.map(|line| {
let (eq_result, equation) = line.split_once(": ").unwrap();
let eq_result = eq_result.parse::<i64>().unwrap();
let numbers = equation
.split(" ")
.map(|num| num.parse::<i64>().unwrap())
.collect::<Vec<i64>>();
let mut operators = vec!["+"; numbers.len() - 1];
let num_combinations = 2_u32.pow(operators.len() as u32);
for _ in 0..num_combinations {
let mut res = numbers[0];
for (num, op) in zip(numbers[1..].iter(), operators.iter()) {
if op == &"+" {
res += num;
}
if op == &"*" {
res *= num;
}
}
if res == eq_result {
return res;
}
operators = binary_add_operators(operators);
}
0
})
.sum()
}
// permutating all combinations of + and * is like counting in binary
fn binary_add_operators(operators: Vec<&str>) -> Vec<&str> {
let mut new_operators = operators.clone();
for (idx, operator) in operators.into_iter().enumerate() {
if operator == "+" {
new_operators[idx] = "*";
break;
}
new_operators[idx] = "+";
}
new_operators
}
pub fn process_part2(input: &str) -> i64 {
input
.lines()
.map(|line| {
let (eq_result, equation) = line.split_once(": ").unwrap();
let eq_result = eq_result.parse::<i64>().unwrap();
let numbers = equation
.split(" ")
.map(|num| num.parse::<i64>().unwrap())
.collect::<Vec<i64>>();
let mut operators = vec!["+"; numbers.len() - 1];
let num_combinations = 3_u32.pow(operators.len() as u32);
for _ in 0..num_combinations {
let mut res = numbers[0];
for (num, op) in zip(numbers[1..].iter(), operators.iter()) {
if op == &"+" {
res += num;
}
if op == &"*" {
res *= num;
}
if op == &"||" {
res = format!("{res}{num}").parse().unwrap();
}
}
if res == eq_result {
return res;
}
operators = ternary_add_operators(operators);
}
0
})
.sum()
}
// permutating all combinations of + and * is like counting in ternary
fn ternary_add_operators(operators: Vec<&str>) -> Vec<&str> {
let mut new_operators = operators.clone();
for (idx, operator) in operators.into_iter().enumerate() {
if operator == "+" {
new_operators[idx] = "*";
break;
} else if operator == "*" {
new_operators[idx] = "||";
break;
}
new_operators[idx] = "+";
}
new_operators
}
#[cfg(test)]
mod tests {
use super::*;
const INPUT: &str = "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";
#[test]
fn part1() {
let result = process_part1(INPUT);
assert_eq!(result, 3749);
}
#[test]
fn part2() {
let result = process_part2(INPUT);
assert_eq!(result, 11387);
}
}

View File

@@ -9,3 +9,5 @@ pub mod d4;
pub mod d5;
pub mod d6;
pub mod d7;