summaryrefslogtreecommitdiff
path: root/2023/src/bin/day_6.rs
diff options
context:
space:
mode:
Diffstat (limited to '2023/src/bin/day_6.rs')
-rw-r--r--2023/src/bin/day_6.rs70
1 files changed, 70 insertions, 0 deletions
diff --git a/2023/src/bin/day_6.rs b/2023/src/bin/day_6.rs
new file mode 100644
index 0000000..138843e
--- /dev/null
+++ b/2023/src/bin/day_6.rs
@@ -0,0 +1,70 @@
+use nom::{
+ bytes::complete::tag,
+ character::complete::{line_ending, space1, u64 as nom_u64},
+ combinator::map,
+ multi::separated_list1,
+ sequence::tuple,
+ IResult,
+};
+use std::fs;
+
+fn main() -> Result<(), Box<dyn std::error::Error>> {
+ let input = fs::read_to_string("inputs/day_6.txt")?;
+ let parsed = RacePlan::multi_parser(&input).unwrap().1;
+ for plan in parsed {
+ dbg!(&plan.win_count_product());
+ }
+
+ Ok(())
+}
+
+#[derive(Debug)]
+struct RacePlan(Vec<RaceRecord>);
+
+#[derive(Debug)]
+struct RaceRecord {
+ time: u64,
+ distance: u64,
+}
+
+impl RacePlan {
+ fn multi_parser(input: &str) -> IResult<&str, Vec<Self>> {
+ separated_list1(line_ending, RacePlan::parser)(input)
+ }
+
+ fn parser(input: &str) -> IResult<&str, Self> {
+ map(
+ tuple((
+ tag("Time:"),
+ space1,
+ separated_list1(space1, nom_u64),
+ line_ending,
+ tag("Distance:"),
+ space1,
+ separated_list1(space1, nom_u64),
+ )),
+ |(_, _, times, _, _, _, distances)| {
+ RacePlan(
+ times
+ .into_iter()
+ .zip(distances.into_iter())
+ .map(|(time, distance)| RaceRecord { time, distance })
+ .collect(),
+ )
+ },
+ )(input)
+ }
+
+ fn win_count_product(&self) -> usize {
+ self.0.iter().map(|r| r.count_wins()).product()
+ }
+}
+
+impl RaceRecord {
+ fn count_wins(&self) -> usize {
+ (1..self.time)
+ .map(|charge_time| charge_time * (self.time - charge_time))
+ .filter(|distance| *distance > self.distance)
+ .count()
+ }
+}