diff --git a/2023/rust/src/day1.rs b/2023/rust/src/day1.rs index c5a32d0..285059d 100644 --- a/2023/rust/src/day1.rs +++ b/2023/rust/src/day1.rs @@ -32,6 +32,72 @@ impl Day1 { Into::::into(first_digit.or(last_digit).unwrap() * 10) + Into::::into(last_digit.or(first_digit).unwrap()) } + + fn num_name(s: &[u8]) -> Option { + for (i, w) in [ + "zero", "one", "two", "three", "four", "five", "six", "seven", "eight", "nine", + ] + .map(|s| s.as_bytes()) + .iter() + .enumerate() + { + if s.starts_with(w) { + return Some(i as u8); + } + } + return None; + } + + fn num_name_end(s: &[u8]) -> Option { + for (i, w) in [ + "zero", "one", "two", "three", "four", "five", "six", "seven", "eight", "nine", + ] + .map(|s| s.as_bytes()) + .iter() + .enumerate() + { + if s.ends_with(w) { + return Some(i as u8); + } + } + return None; + } + + fn calibration_value_words(line: &str) -> i128 { + println!("{line}"); + let bytes = line.as_bytes(); + let mut first_digit: Option = None; + let mut last_digit: Option = None; + for i in 0..bytes.len() { + let n = bytes.len() - 1 - i; + println!("NI: {n} {i}"); + if first_digit.is_none() { + if (0x30..=0x39).contains(&bytes[i]) { + first_digit = Some(bytes[i] - 0x30); + println!("found first {first_digit:?}"); + } else if let Some(n) = Self::num_name(&bytes[i..]) { + first_digit = Some(n); + println!("found first text {first_digit:?}"); + } + } + if last_digit.is_none() { + println!("{:?}", &bytes[..=n]); + if (0x30..=0x39).contains(&bytes[n]) { + last_digit = Some(bytes[n] - 0x30); + println!("found last {last_digit:?}"); + } else if let Some(n) = Self::num_name_end(&bytes[..=n]) { + last_digit = Some(n); + println!("found last text {last_digit:?}"); + } + } + if first_digit.is_some() && last_digit.is_some() { + break; + } + } + println!("{:?} {:?}", first_digit, last_digit); + Into::::into(first_digit.or(last_digit).unwrap() * 10) + + Into::::into(last_digit.or(first_digit).unwrap()) + } } impl AoCSolution for Day1 { @@ -42,8 +108,8 @@ impl AoCSolution for Day1 { input.lines().map(Self::calibration_value).sum() } - fn part2(_input: Self::Input) -> Self::Solution { - return 0; + fn part2(input: Self::Input) -> Self::Solution { + input.lines().map(Self::calibration_value_words).sum() } } @@ -63,6 +129,18 @@ treb7uchet"# ), 142 ); - assert_eq!(Day1::part2("asdf".into()), 0); + assert_eq!( + Day1::part2( + r#"two1nine +eightwothree +abcone2threexyz +xtwone3four +4nineeightseven2 +zoneight234 +7pqrstsixteen"# + .into() + ), + 281 + ); } }