Day 15 - task 2

This commit is contained in:
Jonathan Flueren 2022-12-15 23:16:42 +01:00
parent cb8d6e64ce
commit feccd2992a

View file

@ -1,12 +1,14 @@
use std::{collections::HashSet, fs};
const ROW: i32 = 2000000;
const ROW: i32 = 2_000_000;
const TASK_2_CONST: i32 = 4_000_000;
pub fn solve() {
let path = "res/15/input.txt";
let contents = fs::read_to_string(path).expect("File read error");
// parse sensors as tuples with (sensor, beacon, radius)
let sensors: Vec<((i32, i32), (i32, i32), i32)> = contents
.lines()
.filter(|line| *line != "")
@ -29,10 +31,11 @@ pub fn solve() {
})
.collect();
// task 1
// go through sensors, add x-indices to hashset which are covered by sensors on y=2_000_000
let mut row_map = HashSet::<i32>::new();
sensors.iter().for_each(|sensor| {
let ((x1, y1), (x2, y2), rad) = sensor;
let ((x1, y1), (_, _), rad) = sensor;
let y_diff = y1.abs_diff(ROW) as i32;
let x_diff = rad - y_diff;
@ -44,7 +47,7 @@ pub fn solve() {
row_map.insert(i);
})
});
// remove all x-indices with beacons
sensors.iter().for_each(|sensor| {
let ((_, _), (x2, y2), _) = sensor;
@ -56,47 +59,57 @@ pub fn solve() {
let res = row_map.len();
println!("Result 1: {res}");
let mut sen_tup = Vec::<((i32, i32, i32), (i32, i32, i32))>::new();
let mut up_outlines = Vec::<i32>::new();
let mut down_outlines = Vec::<i32>::new();
sensors.iter().for_each(|s1| {
sensors.iter().for_each(|s2| {
if s1 != s2 {
let ((x1, y1), (_, _), rad1) = *s1;
let ((x2, y2), (_, _), rad2) = *s2;
let dist = x1.abs_diff(x2) as i32 + y1.abs_diff(y2) as i32;
if dist == rad1 + rad2 + 1 {
sen_tup.push(((x1, y1, rad1), (x2, y2, rad2)));
// s2 in quadrant 1
if x1 - x2 < 0 && y1 - y2 > 0 {
down_outlines.push(y1 - (x1 + rad1) - 1)
}
// s2 in quadrant 3
else if x1 - x2 > 0 && y1 - y2 < 0 {
down_outlines.push(y2 - (x2 + rad2) - 1)
}
// s2 in quadrant 2
else if x1 - x2 > 0 && y1 - y2 > 0 {
up_outlines.push(y2 + (x2 + rad2) + 1)
}
// s2 in quadrant 4
else if x1 - x2 < 0 && y1 - y2 < 0 {
up_outlines.push(y1 + (x1 + rad1) + 1)
}
}
}
})
// task 2
// build vec with all outline points of sensor ranges
let mut outline = Vec::<(i32, i32)>::new();
sensors.iter().for_each(|sensor| {
let ((x, y), (_, _), rad) = *sensor;
let mut curr_x = x + rad + 1;
let mut curr_y = y;
for _ in 0..=rad {
curr_x -= 1;
curr_y += 1;
outline.push((curr_x, curr_y));
}
for _ in 0..=rad {
curr_x -= 1;
curr_y -= 1;
outline.push((curr_x, curr_y));
}
for _ in 0..=rad {
curr_x += 1;
curr_y -= 1;
outline.push((curr_x, curr_y));
}
for _ in 0..=rad {
curr_x += 1;
curr_y += 1;
outline.push((curr_x, curr_y));
}
});
let mut intersections = Vec::<(i32, i32)>::new();
up_outlines.iter().for_each(|up_line| {
down_outlines.iter().for_each(|down_line| {
if up_line > down_line && up_line % 2 == down_line % 2 {
let intersection = down_line + (up_line - down_line) / 2;
// TODO continue
// find point that is out of RAD for each sensor
let mut res_point = (-1, -1);
for p in outline {
let mut point_in_sensor_range = false;
for s in &sensors {
let dist = p.0.abs_diff(s.0 .0) as i32 + p.1.abs_diff(s.0 .1) as i32;
if dist <= s.2 {
point_in_sensor_range = true;
break;
}
})
});
}
if !point_in_sensor_range
&& p.0 >= 0
&& p.0 <= TASK_2_CONST
&& p.1 >= 0
&& p.1 <= TASK_2_CONST
{
res_point = p;
break;
}
}
sen_tup.iter().for_each(|tup| {});
let res = TASK_2_CONST as i64 * res_point.0 as i64 + res_point.1 as i64;
println!("Result 2: {res}");
}