Day 1
This commit is contained in:
parent
a24d3134c0
commit
a13b049276
|
@ -1,3 +1,5 @@
|
||||||
|
use std::{collections::HashMap, iter::zip, num::ParseIntError, str::FromStr};
|
||||||
|
|
||||||
use crate::prelude::*;
|
use crate::prelude::*;
|
||||||
|
|
||||||
mod prelude;
|
mod prelude;
|
||||||
|
@ -8,108 +10,57 @@ fn main() {
|
||||||
|
|
||||||
struct Day1 {}
|
struct Day1 {}
|
||||||
impl Day1 {
|
impl Day1 {
|
||||||
fn calibration_value(line: &str) -> i128 {
|
fn smallests_distances(input: &str) -> i64 {
|
||||||
println!("{line}");
|
let mut lefts = Vec::<i64>::new();
|
||||||
let bytes = line.as_bytes();
|
let mut rights = Vec::<i64>::new();
|
||||||
let mut first_digit: Option<u8> = None;
|
for l in input.lines() {
|
||||||
let mut last_digit: Option<u8> = None;
|
let mut tokens = l.split(" ");
|
||||||
for i in 0..bytes.len() {
|
lefts.push(tokens.next().unwrap().parse().unwrap());
|
||||||
let n = bytes.len() - 1 - i;
|
rights.push(tokens.next().unwrap().parse().unwrap());
|
||||||
println!("{n} {i}");
|
|
||||||
if first_digit.is_none() && (0x30..=0x39).contains(&bytes[i]) {
|
|
||||||
first_digit = Some(bytes[i] - 0x30);
|
|
||||||
println!("found first {first_digit:?}");
|
|
||||||
}
|
}
|
||||||
if last_digit.is_none() && (0x30..=0x39).contains(&bytes[n]) {
|
lefts.sort();
|
||||||
last_digit = Some(bytes[n] - 0x30);
|
rights.sort();
|
||||||
println!("found last {last_digit:?}");
|
let mut sum = 0;
|
||||||
|
for (l, r) in zip(&lefts, &rights) {
|
||||||
|
sum += (l - r).abs();
|
||||||
}
|
}
|
||||||
if first_digit.is_some() && last_digit.is_some() {
|
sum
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
println!("{:?} {:?}", first_digit, last_digit);
|
|
||||||
Into::<i128>::into(first_digit.or(last_digit).unwrap() * 10)
|
|
||||||
+ Into::<i128>::into(last_digit.or(first_digit).unwrap())
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fn num_name(s: &[u8]) -> Option<u8> {
|
fn similarity_score(input: &str) -> i64 {
|
||||||
for (i, w) in [
|
let mut lefts = Vec::<i64>::new();
|
||||||
"zero", "one", "two", "three", "four", "five", "six", "seven", "eight", "nine",
|
let mut rights: HashMap<i64, i64> = HashMap::new();
|
||||||
]
|
for l in input.lines() {
|
||||||
.map(|s| s.as_bytes())
|
let mut tokens = l.split(" ");
|
||||||
.iter()
|
lefts.push(tokens.next().unwrap().parse().unwrap());
|
||||||
.enumerate()
|
let right: i64 = tokens.next().unwrap().parse().unwrap();
|
||||||
{
|
match rights.get_mut(&right) {
|
||||||
if s.starts_with(w) {
|
None => {
|
||||||
return Some(i as u8);
|
rights.insert(right, 1);
|
||||||
}
|
}
|
||||||
|
Some(n) => {
|
||||||
|
*n += 1;
|
||||||
}
|
}
|
||||||
return None;
|
};
|
||||||
}
|
}
|
||||||
|
let mut sum = 0;
|
||||||
fn num_name_end(s: &[u8]) -> Option<u8> {
|
for l in &lefts {
|
||||||
for (i, w) in [
|
sum += (rights.get(l).unwrap_or(&0) * l)
|
||||||
"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);
|
|
||||||
}
|
}
|
||||||
}
|
sum
|
||||||
return None;
|
|
||||||
}
|
|
||||||
|
|
||||||
fn calibration_value_words(line: &str) -> i128 {
|
|
||||||
println!("{line}");
|
|
||||||
let bytes = line.as_bytes();
|
|
||||||
let mut first_digit: Option<u8> = None;
|
|
||||||
let mut last_digit: Option<u8> = 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::<i128>::into(first_digit.or(last_digit).unwrap() * 10)
|
|
||||||
+ Into::<i128>::into(last_digit.or(first_digit).unwrap())
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl AoCSolution for Day1 {
|
impl AoCSolution for Day1 {
|
||||||
type Input = String;
|
type Input = String;
|
||||||
type Solution = i128;
|
type Solution = i64;
|
||||||
|
|
||||||
fn part1(input: Self::Input) -> Self::Solution {
|
fn part1(input: Self::Input) -> Self::Solution {
|
||||||
input.lines().map(Self::calibration_value).sum()
|
Day1::smallests_distances(&input)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn part2(input: Self::Input) -> Self::Solution {
|
fn part2(input: Self::Input) -> Self::Solution {
|
||||||
input.lines().map(Self::calibration_value_words).sum()
|
Day1::similarity_score(&input)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -121,26 +72,27 @@ mod tests {
|
||||||
fn test() {
|
fn test() {
|
||||||
assert_eq!(
|
assert_eq!(
|
||||||
Day1::part1(
|
Day1::part1(
|
||||||
r#"1abc2
|
r#"3 4
|
||||||
pqr3stu8vwx
|
4 3
|
||||||
a1b2c3d4e5f
|
2 5
|
||||||
treb7uchet"#
|
1 3
|
||||||
|
3 9
|
||||||
|
3 3"#
|
||||||
.into()
|
.into()
|
||||||
),
|
),
|
||||||
142
|
11
|
||||||
);
|
);
|
||||||
assert_eq!(
|
assert_eq!(
|
||||||
Day1::part2(
|
Day1::part2(
|
||||||
r#"two1nine
|
r#"3 4
|
||||||
eightwothree
|
4 3
|
||||||
abcone2threexyz
|
2 5
|
||||||
xtwone3four
|
1 3
|
||||||
4nineeightseven2
|
3 9
|
||||||
zoneight234
|
3 3"#
|
||||||
7pqrstsixteen"#
|
|
||||||
.into()
|
.into()
|
||||||
),
|
),
|
||||||
281
|
31
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -6,8 +6,10 @@ use std::{env, io};
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
enum InputFileError {
|
enum InputFileError {
|
||||||
#![allow(dead_code)]
|
#[allow(dead_code)]
|
||||||
EnvVar(env::VarError),
|
EnvVar(env::VarError),
|
||||||
|
|
||||||
|
#[allow(dead_code)]
|
||||||
Io(io::Error),
|
Io(io::Error),
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue