From 274266a31829e86512f9ce5edc818e1381511236 Mon Sep 17 00:00:00 2001 From: Justin Wernick Date: Sat, 10 Dec 2022 11:52:15 +0200 Subject: Day 10 --- 2022/src/bin/day_10.rs | 103 +++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 103 insertions(+) create mode 100644 2022/src/bin/day_10.rs (limited to '2022/src/bin') diff --git a/2022/src/bin/day_10.rs b/2022/src/bin/day_10.rs new file mode 100644 index 0000000..6999c52 --- /dev/null +++ b/2022/src/bin/day_10.rs @@ -0,0 +1,103 @@ +use nom::{ + bytes::complete::tag, + character::complete::{i32, line_ending}, + combinator::map, + multi::{many0, separated_list1}, + sequence::{pair, tuple}, + IResult, +}; +use std::fs; + +fn main() -> Result<(), Box> { + let input = fs::read_to_string("inputs/day_10.txt")?; + let program = Program::parser(&input).unwrap().1; + let result = program.process(); + + dbg!(result.sum_of_signal_strengths(&[20, 60, 100, 140, 180, 220])); + + for y in 0..6 { + for x in 0..40 { + if result.pixel_should_activate(x, y) { + print!("#"); + } else { + print!("."); + } + } + println!(); + } + Ok(()) +} + +#[derive(Debug)] +struct Program(Vec); + +#[derive(Debug, Default)] +struct ProgramResult(Vec); + +#[derive(Debug, Clone)] +struct TimeSequence { + time: u32, + value: i32, +} + +impl Program { + fn parser(input: &str) -> IResult<&str, Self> { + map(separated_list1(line_ending, TimeSequence::parser), Program)(input) + } + + fn process(&self) -> ProgramResult { + let mut result = ProgramResult::default(); + + let mut current_state = TimeSequence { time: 1, value: 1 }; + result.0.push(current_state.clone()); + + for next_step in &self.0 { + current_state.time += next_step.time; + current_state.value += next_step.value; + result.0.push(current_state.clone()); + } + + result + } +} + +impl TimeSequence { + fn parser(input: &str) -> IResult<&str, Self> { + map( + tuple((many0(pair(tag("noop"), line_ending)), tag("addx "), i32)), + |(noops, _, value)| TimeSequence { + time: noops.len() as u32 + 2, + value, + }, + )(input) + } +} + +impl ProgramResult { + fn value_at(&self, time: u32) -> i32 { + self.0 + .iter() + .filter(|t| t.time <= time) + .map(|t| t.value) + .last() + .unwrap_or(0) + } + + fn signal_strength_at(&self, time: u32) -> i32 { + let value = self.value_at(time); + value * time as i32 + } + + fn sum_of_signal_strengths(&self, times: &[u32]) -> i32 { + times + .iter() + .map(|time| self.signal_strength_at(*time)) + .sum() + } + + fn pixel_should_activate(&self, x: usize, y: usize) -> bool { + let time = (y * 40 + x + 1) as u32; + let sprite_middle = self.value_at(time); + ((x as i32) - sprite_middle).abs() <= 1 + } +} -- cgit v1.2.3