feat: added day 8 part 1 and 2
All checks were successful
Build and run challenges / Challenge for day (4) (push) Successful in 5s
Build and run challenges / Challenge for day (5) (push) Successful in 5s
Build and run challenges / Challenge for day (3) (push) Successful in 11s
Build and run challenges / Challenge for day (8) (push) Successful in 3s
Build and run challenges / Challenge for day (1) (push) Successful in 3s
Build and run challenges / Challenge for day (6) (push) Successful in 5s
Build and run challenges / Challenge for day (7) (push) Successful in 4s
Build and run challenges / Challenge for day (2) (push) Successful in 3s
All checks were successful
Build and run challenges / Challenge for day (4) (push) Successful in 5s
Build and run challenges / Challenge for day (5) (push) Successful in 5s
Build and run challenges / Challenge for day (3) (push) Successful in 11s
Build and run challenges / Challenge for day (8) (push) Successful in 3s
Build and run challenges / Challenge for day (1) (push) Successful in 3s
Build and run challenges / Challenge for day (6) (push) Successful in 5s
Build and run challenges / Challenge for day (7) (push) Successful in 4s
Build and run challenges / Challenge for day (2) (push) Successful in 3s
Signed-off-by: Louis Vallat <contact@louis-vallat.dev>
This commit is contained in:
parent
005bdb82af
commit
013414d7a3
@ -11,7 +11,7 @@ jobs:
|
||||
name: Challenge for day
|
||||
strategy:
|
||||
matrix:
|
||||
day_number: [1, 2, 3, 4, 5, 6, 7]
|
||||
day_number: [1, 2, 3, 4, 5, 6, 7, 8]
|
||||
runs-on: rust-bookworm
|
||||
steps:
|
||||
- name: Check out repository code
|
||||
|
6
day8/Cargo.toml
Normal file
6
day8/Cargo.toml
Normal file
@ -0,0 +1,6 @@
|
||||
[package]
|
||||
name = "day8"
|
||||
version = "0.1.0"
|
||||
edition = "2021"
|
||||
|
||||
[dependencies]
|
114
day8/src/main.rs
Normal file
114
day8/src/main.rs
Normal file
@ -0,0 +1,114 @@
|
||||
use std::collections::{HashMap, HashSet};
|
||||
use std::{env, fs};
|
||||
|
||||
fn read_input(path: &str) -> String {
|
||||
fs::read_to_string(path).expect("Cannot read file.")
|
||||
}
|
||||
|
||||
fn parse_input(input: &str) -> (HashMap<char, HashSet<(i32, i32)>>, (i32, i32)) {
|
||||
let mut antenna_positions: HashMap<char, HashSet<(i32, i32)>> = HashMap::new();
|
||||
let mut dimensions = (0, 0);
|
||||
for (row, line) in input.lines().filter(|line| !line.is_empty()).enumerate() {
|
||||
dimensions.0 = row + 1;
|
||||
for (col, c) in line.chars().enumerate() {
|
||||
dimensions.1 = col + 1;
|
||||
if c != '.' {
|
||||
if let Some(positions) = antenna_positions.get_mut(&c) {
|
||||
positions.insert((row as i32, col as i32));
|
||||
} else {
|
||||
antenna_positions.insert(c, HashSet::from_iter(vec![(row as i32, col as i32)]));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
(
|
||||
antenna_positions,
|
||||
(dimensions.0 as i32, dimensions.1 as i32),
|
||||
)
|
||||
}
|
||||
|
||||
fn get_anti_nodes_positions_in_map(
|
||||
start: &(i32, i32),
|
||||
direction: &(i32, i32),
|
||||
map_size: &(i32, i32),
|
||||
limit: Option<i32>,
|
||||
) -> HashSet<(i32, i32)> {
|
||||
let mut anti_nodes_locations = HashSet::new();
|
||||
let init = if limit.is_some() { 1 } else { 0 };
|
||||
|
||||
for i in init.. {
|
||||
let x = (start.0 + direction.0 * i, start.1 + direction.1 * i);
|
||||
if !(0..map_size.0).contains(&x.0) || !(0..map_size.1).contains(&x.1) {
|
||||
return anti_nodes_locations;
|
||||
}
|
||||
anti_nodes_locations.insert(x);
|
||||
if limit.is_some() && i >= limit.unwrap() {
|
||||
return anti_nodes_locations;
|
||||
}
|
||||
}
|
||||
anti_nodes_locations
|
||||
}
|
||||
|
||||
fn compute_anti_nodes_count(
|
||||
antenna_positions: &HashMap<char, HashSet<(i32, i32)>>,
|
||||
map_size: &(i32, i32),
|
||||
limit: Option<i32>,
|
||||
) -> usize {
|
||||
let mut computed_pairs = HashSet::new();
|
||||
let mut anti_nodes_locations: HashSet<(i32, i32)> = HashSet::new();
|
||||
|
||||
for positions in antenna_positions.values() {
|
||||
for x in positions.iter() {
|
||||
for y in positions.iter() {
|
||||
if x != y && !computed_pairs.contains(&(y, x)) {
|
||||
computed_pairs.insert((x, y));
|
||||
anti_nodes_locations.extend(
|
||||
get_anti_nodes_positions_in_map(
|
||||
&y,
|
||||
&(y.0 - x.0, y.1 - x.1),
|
||||
map_size,
|
||||
limit,
|
||||
)
|
||||
.iter(),
|
||||
);
|
||||
anti_nodes_locations.extend(
|
||||
get_anti_nodes_positions_in_map(
|
||||
&x,
|
||||
&(x.0 - y.0, x.1 - y.1),
|
||||
map_size,
|
||||
limit,
|
||||
)
|
||||
.iter(),
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
anti_nodes_locations.len()
|
||||
}
|
||||
|
||||
fn part_1(antenna_positions: &HashMap<char, HashSet<(i32, i32)>>, map_size: &(i32, i32)) -> usize {
|
||||
compute_anti_nodes_count(antenna_positions, map_size, Some(1))
|
||||
}
|
||||
|
||||
fn part_2(antenna_positions: &HashMap<char, HashSet<(i32, i32)>>, map_size: &(i32, i32)) -> usize {
|
||||
compute_anti_nodes_count(antenna_positions, map_size, None)
|
||||
}
|
||||
|
||||
fn main() {
|
||||
let args: Vec<String> = env::args().collect();
|
||||
for arg in args.iter().skip(1) {
|
||||
let input = read_input(&arg);
|
||||
let (antenna_positions, map_size) = parse_input(&input);
|
||||
println!("[{}]", &arg);
|
||||
println!(
|
||||
"\t[Part 1] => Answer is '{}'.",
|
||||
part_1(&antenna_positions, &map_size)
|
||||
);
|
||||
println!(
|
||||
"\t[Part 2] => Answer is '{}'.",
|
||||
part_2(&antenna_positions, &map_size)
|
||||
);
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue
Block a user