From 1bde2efe2129fee401cf79d4fbb7cd44c30d3c5e Mon Sep 17 00:00:00 2001 From: Joey Pollack Date: Thu, 12 Dec 2024 16:30:46 -0500 Subject: [PATCH] working on day 8 --- Cargo.lock | 9 ++ Cargo.toml | 6 +- crates/day_8/data/day8_input | 50 ++++++++ crates/day_8/data/day8_test_input | 12 ++ crates/day_8/src/day_8.rs | 23 +++- crates/day_8/src/lib.rs | 3 +- crates/day_8/src/map.rs | 182 ++++++++++++++++++++++++++++++ crates/day_9/Cargo.toml | 9 ++ crates/day_9/build.rs | 33 ++++++ crates/day_9/data/day9_input | 0 crates/day_9/data/day9_test_input | 0 crates/day_9/src/day_9.rs | 96 ++++++++++++++++ crates/day_9/src/lib.rs | 2 + crates/utils/src/lib.rs | 2 +- src/main.rs | 4 +- 15 files changed, 423 insertions(+), 8 deletions(-) create mode 100644 crates/day_8/src/map.rs create mode 100644 crates/day_9/Cargo.toml create mode 100644 crates/day_9/build.rs create mode 100644 crates/day_9/data/day9_input create mode 100644 crates/day_9/data/day9_test_input create mode 100644 crates/day_9/src/day_9.rs create mode 100644 crates/day_9/src/lib.rs diff --git a/Cargo.lock b/Cargo.lock index 9a976ea..05891f7 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -14,6 +14,7 @@ dependencies = [ "day_6", "day_7", "day_8", + "day_9", "solver_base", "utils", ] @@ -104,6 +105,14 @@ dependencies = [ "utils", ] +[[package]] +name = "day_9" +version = "0.1.0" +dependencies = [ + "solver_base", + "utils", +] + [[package]] name = "matrixmultiply" version = "0.3.9" diff --git a/Cargo.toml b/Cargo.toml index 6542d48..b7a63b6 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -4,7 +4,6 @@ version = "0.1.0" edition = "2021" [workspace] -# resolver = "2" # Important! wgpu/Bevy needs this! .. so not important for this project? members = [ "crates/utils", "crates/solver_base", @@ -16,6 +15,7 @@ members = [ "crates/day_6", "crates/day_7", "crates/day_8", + "crates/day_9", ] [dependencies] @@ -29,6 +29,7 @@ day_5 = { workspace = true } day_6 = { workspace = true } day_7 = { workspace = true } day_8 = { workspace = true } +day_9 = { workspace = true } [workspace.dependencies] @@ -41,4 +42,5 @@ day_4 = { path = "crates/day_4" } day_5 = { path = "crates/day_5" } day_6 = { path = "crates/day_6" } day_7 = { path = "crates/day_7" } -day_8 = { path = "crates/day_8" } \ No newline at end of file +day_8 = { path = "crates/day_8" } +day_9 = { path = "crates/day_9" } \ No newline at end of file diff --git a/crates/day_8/data/day8_input b/crates/day_8/data/day8_input index e69de29..2db96dd 100644 --- a/crates/day_8/data/day8_input +++ b/crates/day_8/data/day8_input @@ -0,0 +1,50 @@ +.............C.7..................G..0...y........ +..................7................C.............. +....................................0......W....y. +.......................................D..W....... +..........u....................................... +..................................4.......D0...j.. +.....................................D............ +................O.....C................G.......... +............F.....................C............... +......u..........F.................4.......y...... +..........X..........5....4...........1........... +..........F...........5X...................3...... +.............F.............................j.3.... +.................u..............X................. +............................7..................... +.................................................. +..........................5.....j2.........4...... +....d.....................y...................j1.. +.................................................. +............................Y.e................... +.................d...X...............J...........e +.............d.................................... +..............................Y..............1.... +.........................................Y........ +......................W......8..f...J.........3... +.......w.............J............................ +...................................U.....f......e. +.................................Of....e....t...1. +.......g..........d......s........................ +................G................f................ +.....................................O............ +...g........................T.....U............... +......................s..........T.............G.. +................................s.......8......... +.....9........g...........o...U............E...... +............g............................t....o... +...........................................6....E. +.....................s......x........6....E....... +..........w.9................x............t....... +...........9........w...........J.....6o.......... +.............................................o.... +..........S................U...................... +.......S..2..........c........T.O....t............ +.....2...S.....c...................T.............. +..................x.......................8....... +....9............................................. +...wS.....................................6....... +................2........................8........ +.................................................. +.................x....c........................E.. \ No newline at end of file diff --git a/crates/day_8/data/day8_test_input b/crates/day_8/data/day8_test_input index e69de29..de0f909 100644 --- a/crates/day_8/data/day8_test_input +++ b/crates/day_8/data/day8_test_input @@ -0,0 +1,12 @@ +............ +........0... +.....0...... +.......0.... +....0....... +......A..... +............ +............ +........A... +.........A.. +............ +............ \ No newline at end of file diff --git a/crates/day_8/src/day_8.rs b/crates/day_8/src/day_8.rs index 28a55b3..7670e39 100644 --- a/crates/day_8/src/day_8.rs +++ b/crates/day_8/src/day_8.rs @@ -11,6 +11,8 @@ use ::solver_base::solver_base::{Solver, DataSet, RunMode}; use utils::utils; +use crate::map::Map; + pub struct Day8 { data_set: DataSet, @@ -19,6 +21,8 @@ pub struct Day8 do_verbose_prints: bool, pub final_result: i32, + + map: Map, } //||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||| @@ -33,7 +37,9 @@ impl Day8 run_mode: RunMode::FirstCase, do_debug_prints: false, do_verbose_prints: false, - final_result: 0 + final_result: 0, + + map: Map::new(), } } @@ -71,9 +77,20 @@ impl Solver for Day8 DataSet::Full => format!("{}/data/day8_input", dir), }; - let _data = utils::load_data(&data_filename); + let data = utils::load_data(&data_filename); + + self.map = Map::parse(&data); + + if self.do_debug_prints + { + self.map.print(false); - // TODO: Day8::init + if !self.map.double_check_antenna_locations() + { + println!("ERROR: Antenna locations map is broken!"); + //self.map.print_ant_locations(); + } + } } diff --git a/crates/day_8/src/lib.rs b/crates/day_8/src/lib.rs index 21a1686..29ddf89 100644 --- a/crates/day_8/src/lib.rs +++ b/crates/day_8/src/lib.rs @@ -1,2 +1,3 @@ -pub mod day_8; \ No newline at end of file +pub mod day_8; +pub mod map; \ No newline at end of file diff --git a/crates/day_8/src/map.rs b/crates/day_8/src/map.rs new file mode 100644 index 0000000..c9b7738 --- /dev/null +++ b/crates/day_8/src/map.rs @@ -0,0 +1,182 @@ +/****************************************************************************** +* @file map.rs +* @author Joey Pollack +* @date 2024/12/12 (y/m/d) +* @modified 2024/12/12 (y/m/d) +* @copyright Joseph R Pollack +* @brief Represents the map of antennas +******************************************************************************/ + +// Each antenna is tuned to a specific frequency indicated by a +// single lowercase letter, uppercase letter, or digit. + +// an antinode occurs at any point that is perfectly in line with two antennas of the same +// frequency - but only when one of the antennas is twice as far away as the other +// This means that for any pair of antennas with the same frequency, there are two antinodes, one on either side of them. + +// So, for these two antennas with frequency `a`, they create the two antinodes marked with `#`: + +// .......... +// ...#...... +// .......... +// ....a..... +// .......... +// .....a.... +// .......... +// ......#... +// .......... +// .......... + +use std::{collections::HashMap, mem}; + + +#[derive(Copy, Clone, PartialEq, Debug)] +pub enum MapCell +{ + Empty, + Freq(u8), + +} + +#[derive(Copy, Clone, PartialEq, Debug)] +pub struct PointIdx +{ + i: usize, + j: usize, +} + +impl PointIdx +{ + pub fn new(i: usize, j: usize) -> PointIdx + { + PointIdx { i, j } + } +} + +#[derive(Clone, Debug)] +pub struct Map +{ + map: Vec>, + antenna_locations: HashMap>, + antinodes: Vec, +} + +impl Map +{ + pub fn new() -> Map + { + Map { map: vec![], antenna_locations: HashMap::new(), antinodes: vec![] } + } + + pub fn parse(data: &str) -> Map + { + let mut split_pattern = "\n"; + if data.contains("\r\n") + { + split_pattern = "\r\n"; + } + + let mut map: Vec> = vec![]; + let mut antenna_locations: HashMap> = HashMap::new(); + + for row in data.split(split_pattern) + { + let mut parsed_row: Vec = vec![]; + for c in row.as_bytes().into_iter() + { + match *c + { + b'.' => parsed_row.push(MapCell::Empty), + b'0'..=b'9' | b'a'..=b'z' | b'A'..=b'Z' => + { + parsed_row.push(MapCell::Freq(*c)); + + if !antenna_locations.contains_key(c) + { + antenna_locations.insert(*c, vec![]); + } + + if let Some(loc_vec) = antenna_locations.get_mut(c) + { + loc_vec.push(PointIdx::new(map.len(), parsed_row.len() - 1)); + } + else + { + panic!("ERROR: antenna_location does not contain the vector that should have literally just been added to it????") + } + }, + + _ => panic!("ERROR: Unknown map cell type: {}", *c) + } + } + + map.push(parsed_row); + } + + Map { map, antenna_locations, antinodes: vec![] } + } + + pub fn double_check_antenna_locations(self: &Map) -> bool + { + for (i, row) in self.map.iter().enumerate() + { + for (j, c) in row.iter().enumerate() + { + if mem::discriminant(c) == mem::discriminant(&MapCell::Freq(0)) + { + if let MapCell::Freq(f) = c + { + if !self.antenna_locations[f].contains(&PointIdx::new(i, j)) + { + println!("ERROR: Incorrect Antenna Location! Actual: ({}, {}), Locations for this frequency ({}): {:#?}", + i, j, *f as char, self.antenna_locations); + return false; + } + } + } + } + } + + true + } + + pub fn print(self: &Map, include_antinodes: bool) + { + print!("MAP:"); + for (i, row) in self.map.iter().enumerate() + { + print!("\n\t"); + for (j, c) in row.iter().enumerate() + { + if include_antinodes && self.antinodes.contains(&PointIdx::new(i, j)) + { + print!("#"); + } + else + { + match c + { + MapCell::Empty => print!("."), + MapCell::Freq(f) => print!("{}", *f as char), + } + } + } + } + println!(); + } + + pub fn print_ant_locations(self: &Map) + { + println!("{:#?}", self.antenna_locations); + } + + pub fn find_antinodes(self: &mut Map) -> Vec + { + for ant in &self.antenna_locations + { + + } + + vec![] + } +} \ No newline at end of file diff --git a/crates/day_9/Cargo.toml b/crates/day_9/Cargo.toml new file mode 100644 index 0000000..babdd77 --- /dev/null +++ b/crates/day_9/Cargo.toml @@ -0,0 +1,9 @@ +[package] +name = "day_9" +description = "Day 9 of the Advent of Code 2024" +version = "0.1.0" +edition = "2021" + +[dependencies] +solver_base = { workspace = true } +utils = { workspace = true } \ No newline at end of file diff --git a/crates/day_9/build.rs b/crates/day_9/build.rs new file mode 100644 index 0000000..4cd9495 --- /dev/null +++ b/crates/day_9/build.rs @@ -0,0 +1,33 @@ + +use std::{env, fs, path::Path}; + +fn main() +{ + // let out_dir = env::var("OUT_DIR").unwrap(); + // let cwd = env::var("CARGO_MANIFEST_DIR").unwrap(); + // println!("CWD: {}\n", cwd); + // let data_dir = cwd + "\\data"; + // let data_path = Path::new(&data_dir); + // println!("Data path: {}", data_path.to_string_lossy()); + + // let data_path = Path::new("data/test_input"); + + // let out_dir = env::var("OUT_DIR").unwrap(); + // panic!("out_dir: {}", out_dir); + let out_path = format!("../../target/{}", &env::var("PROFILE").unwrap()); + let out_path = Path::new(&out_path); + //let out_path = Path::new(&out_dir).join(&env::var("PROFILE").unwrap()); + let out_path_data = out_path.join(Path::new("data")); + + if !out_path_data.exists() + { + fs::create_dir(&out_path_data).expect(&format!("Could not create data directory at: {}", out_path_data.to_string_lossy())); + } + + for file in fs::read_dir("data").unwrap() + { + let file = file.unwrap(); + let dest = out_path.join(file.path()); + fs::copy(file.path(), &dest).expect(&format!("Could not copy file {} to {}", file.path().to_string_lossy(), dest.to_string_lossy())); + } +} \ No newline at end of file diff --git a/crates/day_9/data/day9_input b/crates/day_9/data/day9_input new file mode 100644 index 0000000..e69de29 diff --git a/crates/day_9/data/day9_test_input b/crates/day_9/data/day9_test_input new file mode 100644 index 0000000..e69de29 diff --git a/crates/day_9/src/day_9.rs b/crates/day_9/src/day_9.rs new file mode 100644 index 0000000..ce513f7 --- /dev/null +++ b/crates/day_9/src/day_9.rs @@ -0,0 +1,96 @@ + +/****************************************************************************** +* @file day_9.rs +* @author Joey Pollack +* @date 2024/12/05 (y/m/d) +* @modified 2024/12/05 (y/m/d) +* @copyright Joseph R Pollack +* @brief Advent of Code 2024 day 9 problems +******************************************************************************/ + +use ::solver_base::solver_base::{Solver, DataSet, RunMode}; +use utils::utils; + +pub struct Day9 +{ + data_set: DataSet, + run_mode: RunMode, + do_debug_prints: bool, + do_verbose_prints: bool, + + pub final_result: i32, +} + +//||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||| +// DAY 9 IMPL +//||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||| +impl Day9 +{ + pub fn new() -> Day9 + { + Day9 { + data_set: DataSet::Test, + run_mode: RunMode::FirstCase, + do_debug_prints: false, + do_verbose_prints: false, + final_result: 0 + } + } + + fn solve_first_case(self: &mut Self) -> String + { + + self.final_result.to_string() + } + + fn solve_second_case(self: &mut Self) -> String + { + + self.final_result.to_string() + } +} + +//||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||| +// SOLVER TRAIT IMPL +//||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||| +impl Solver for Day9 +{ + fn init(self: &mut Self, data_set: DataSet, run_mode: RunMode, enable_debug_prints: bool, enable_verbose_prints: bool) + { + self.data_set = data_set; + self.run_mode = run_mode; + self.do_debug_prints = enable_debug_prints; + self.do_verbose_prints = enable_verbose_prints; + + let dir = utils::get_working_dir(); + let data_filename = + match self.data_set + { + DataSet::Test => format!("{}/data/day9_test_input", dir), + DataSet::TestAlt => panic!("Day 9: There is no TestAlt input file!"), //format!("{}/data/day2_test_input", dir), + DataSet::Full => format!("{}/data/day9_input", dir), + }; + + let _data = utils::load_data(&data_filename); + + // TODO: Day9::init + + } + + fn solve(self: &mut Self) -> String + { + match self.run_mode + { + RunMode::FirstCase => + { + self.solve_first_case() + }, + + RunMode::SecondCase => + { + self.solve_second_case() + } + } + } + +} \ No newline at end of file diff --git a/crates/day_9/src/lib.rs b/crates/day_9/src/lib.rs new file mode 100644 index 0000000..53e0a72 --- /dev/null +++ b/crates/day_9/src/lib.rs @@ -0,0 +1,2 @@ + +pub mod day_9; \ No newline at end of file diff --git a/crates/utils/src/lib.rs b/crates/utils/src/lib.rs index beff5a2..a8bf341 100644 --- a/crates/utils/src/lib.rs +++ b/crates/utils/src/lib.rs @@ -1,2 +1,2 @@ -pub mod utils; \ No newline at end of file +pub mod utils; diff --git a/src/main.rs b/src/main.rs index 065cf40..8fc7576 100644 --- a/src/main.rs +++ b/src/main.rs @@ -16,12 +16,13 @@ use day_4::day_4::Day4; use day_5::day_5::Day5; use day_6::day_6::Day6; use day_7::day_7::Day7; +use day_8::day_8::Day8; use solver_base::solver_base::{Solver, DataSet, RunMode}; use settings::Settings; fn main() { - const NUM_PROBLEMS: i32 = 7; + const NUM_PROBLEMS: i32 = 8; let program_settings = Settings::new(); for i in 1..=NUM_PROBLEMS @@ -67,6 +68,7 @@ fn create_problem_solver(day_num: i32) -> Box 5 => Box::new(Day5::new()), 6 => Box::new(Day6::new()), 7 => Box::new(Day7::new()), + 8 => Box::new(Day8::new()), _ => panic!("ERROR in create_problem_solver: Invalid day_num: {}", day_num) }