From d0f307bc02b5e87e75dcd23242b06f2c763d3af4 Mon Sep 17 00:00:00 2001 From: erius Date: Tue, 5 Dec 2023 16:50:04 +0300 Subject: [PATCH] Seperated solutions into different binaries Implemented day 3 part 1 solution --- src/bin/day1.rs | 32 +++++++++++++++++++++++++ src/bin/day2.rs | 51 +++++++++++++++++++++++++++++++++++++++ src/bin/day3.rs | 63 +++++++++++++++++++++++++++++++++++++++++++++++++ src/main.rs | 55 ------------------------------------------ 4 files changed, 146 insertions(+), 55 deletions(-) create mode 100644 src/bin/day1.rs create mode 100644 src/bin/day2.rs create mode 100644 src/bin/day3.rs delete mode 100644 src/main.rs diff --git a/src/bin/day1.rs b/src/bin/day1.rs new file mode 100644 index 0000000..5b6eba9 --- /dev/null +++ b/src/bin/day1.rs @@ -0,0 +1,32 @@ +fn main() { + let input = std::fs::read_to_string("input/1.txt").unwrap(); + let (result1, result2) = (part1(&input), part2(&input)); + println!("Day 1"); + println!("Part 1: {}", result1); + println!("Part 2: {}", result2); + println!(); +} + +fn part1(input: &str) -> u128 { + let mut result = 0_u128; + for line in input.lines() { + let mut digits_only = String::new(); + for c in line.chars() { if c.is_digit(10) { digits_only.push(c); } } + let mut calibration = String::new(); + calibration += &digits_only[..1]; + calibration += &digits_only[digits_only.len() - 1..]; + let value: u128 = calibration.parse().unwrap(); + result += value; + } + result +} + +fn part2(input: &str) -> u128 { + let str_to_digit = std::collections::HashMap::from([ + ("one", "o1e"), ("two", "t2o"), ("three", "t3e"), ("four", "4"), + ("five", "5e"), ("six", "6"), ("seven", "7n"), ("eight", "e8t"), ("nine", "n9e") + ]); + let mut input: String = input.into(); + for (str, digit) in str_to_digit.iter() { input = input.replace(str, digit); } + part1(&input) +} diff --git a/src/bin/day2.rs b/src/bin/day2.rs new file mode 100644 index 0000000..dad8a01 --- /dev/null +++ b/src/bin/day2.rs @@ -0,0 +1,51 @@ +fn main() { + let input = std::fs::read_to_string("input/2.txt").unwrap(); + let (result1, result2) = (part1(&input, 12, 13, 14), part2(&input)); + println!("Day 2"); + println!("Part 1: {}", result1); + println!("Part 2: {}", result2); + println!(); +} + +fn part1(input: &str, red: u8, green: u8, blue: u8) -> u128 { + let bag_contents = std::collections::HashMap::from([ + ("red", red), ("green", green), ("blue", blue) + ]); + let mut result = 0_u128; + 'games_loop: + for line in input.lines() { + let (game_id, game_data) = line.split_once(':').unwrap(); + let (_, game_id) = game_id.split_once(' ').unwrap(); + let game_id: u128 = game_id.parse().unwrap(); + for cubes in game_data.split(';') { + for colored_cubes in cubes.split(',') { + let (amount, color) = colored_cubes.trim().split_once(' ').unwrap(); + let amount: u8 = amount.parse().unwrap(); + if bag_contents[color] < amount { continue 'games_loop; } + } + } + result += game_id; + } + result +} + +fn part2(input: &str) -> u128 { + let mut result = 0_u128; + for line in input.lines() { + let mut possible_game_cubes = std::collections::HashMap::from([ + ("red", u8::MIN), ("green", u8::MIN), ("blue", u8::MIN) + ]); + let (_, game_data) = line.split_once(':').unwrap(); + for cubes in game_data.split(';') { + for colored_cubes in cubes.split(',') { + let (amount, color) = colored_cubes.trim().split_once(' ').unwrap(); + let amount: u8 = amount.parse().unwrap(); + possible_game_cubes.insert(color, possible_game_cubes[color].max(amount)); + } + } + let power: u128 = possible_game_cubes.values().map(|e| *e as u128).product(); + result += power; + } + result +} + diff --git a/src/bin/day3.rs b/src/bin/day3.rs new file mode 100644 index 0000000..ab62883 --- /dev/null +++ b/src/bin/day3.rs @@ -0,0 +1,63 @@ +fn main() { + let input = std::fs::read_to_string("input/3.txt").unwrap(); + let (result1, result2) = (part1(&input), 0); + println!("Day 3"); + println!("Part 1: {}", result1); + println!("Part 2: {}", result2); + println!(); +} + +fn adjacent_numbers(lines: &Vec<&str>, line_index: usize, char_index: usize) -> Vec { + let mut numbers: Vec = vec![]; + for dy in -1..=1 { + let line_offsetted_index = (line_index as i32 + dy) as usize; + let line = lines[line_offsetted_index]; + for dx in -1..=1 { + if dx == 0 && dy == 0 { continue; } + let char_offsetted_index = (char_index as i32 + dx) as usize; + let c = line.as_bytes()[char_offsetted_index] as char; + if !c.is_digit(10) { continue; } + let number = find_full_number(line, char_offsetted_index, c); + numbers.push(number); + } + let row_left = &line[char_index - 1..=char_index]; + if row_left.chars().filter(|c| c .is_digit(10)).count() == 2 { numbers.pop(); } + let row_right = &line[char_index..=char_index + 1]; + if row_right.chars().filter(|c| c.is_digit(10)).count() == 2 { numbers.pop(); } + } + numbers +} + +fn find_full_number(line: &str, char_index: usize, character: char) -> u128 { + let (mut left_side, mut right_side) = (String::new(), String::new()); + for i in char_index + 1..line.len() { + let c = line.as_bytes()[i] as char; + if !c.is_digit(10) { break; } + right_side.push(c); + } + for i in (0..char_index).rev() { + let c = line.as_bytes()[i] as char; + if !c.is_digit(10) { break; } + left_side.push(c); + } + left_side = left_side.chars().rev().collect(); + let number = left_side + &character.to_string() + &right_side; + let number = number.parse().unwrap(); + number +} + +fn part1(input: &str) -> u128 { + let lines: Vec<&str> = input.lines().collect(); + let mut result = 0_u128; + for i in 1..lines.len() - 1 { + let line = lines[i]; + for (j, c) in line.chars().enumerate() { + if c == '.' || c.is_digit(10) { continue; } + let numbers = adjacent_numbers(&lines, i, j); + let sum: u128 = numbers.iter().sum(); + result += sum; + } + } + result +} + diff --git a/src/main.rs b/src/main.rs deleted file mode 100644 index 5cee901..0000000 --- a/src/main.rs +++ /dev/null @@ -1,55 +0,0 @@ -#![allow(dead_code)] -use std::collections::HashMap; - -fn main() { - day3(); -} - -fn day1() { - let str_to_digit = HashMap::from([ - ("one", "o1e"), ("two", "t2o"), ("three", "t3e"), ("four", "4"), - ("five", "5e"), ("six", "6"), ("seven", "7n"), ("eight", "e8t"), ("nine", "n9e") - ]); - let input = std::fs::read_to_string("input/1.txt").unwrap(); - let mut result = 0_u128; - for line in input.lines() { - let mut line = String::from(line); - for (str, digit) in str_to_digit.iter() { line = line.replace(str, digit); } - let mut digits_only = String::new(); - for c in line.chars() { if c.is_digit(10) { digits_only.push(c); } } - let mut calibration = String::new(); - calibration += &digits_only[..1]; - calibration += &digits_only[digits_only.len() - 1..]; - let value: u128 = calibration.parse().unwrap(); - result += value; - } - println!("{}", result); -} - -fn day2() { - let input = std::fs::read_to_string("input/2.txt").unwrap(); - let mut result = 0_u128; - for line in input.lines() { - let mut possible_game_cubes = HashMap::from([ - ("red", u8::MIN), ("green", u8::MIN), ("blue", u8::MIN) - ]); - let (_, game_data) = line.split_once(':').unwrap(); - for cubes in game_data.split(';') { - for colored_cubes in cubes.split(',') { - let (amount, color) = colored_cubes.trim().split_once(' ').unwrap(); - let amount: u8 = amount.parse().unwrap(); - possible_game_cubes.insert(color, possible_game_cubes[color].max(amount)); - } - } - let power: u128 = possible_game_cubes.values().map(|e| *e as u128).product(); - result += power; - } - println!("{}", result); -} - -fn day3() { - let input = std::fs::read_to_string("input/3.txt").unwrap(); - let mut result = 0_u128; - -} -