1
Fork 0
advent-of-code/source/year_2021/day_10/mod.rs

88 lines
1.8 KiB
Rust

use crate::prelude::*;
pub fn solution() -> Solution {
Solution::new(Day::new(10, 2021), part_1, part_2)
.with_expected(387363, 4330777059_i64)
}
fn part_1(input: &str) -> Result<String> {
let mut syntax_error_score = 0;
for line in input.lines() {
let mut tokens = VecDeque::new();
for token in line.chars() {
if ['(', '[', '{', '<'].contains(&token) {
tokens.push_back(token);
continue;
}
let expected_close = match tokens.pop_back() {
Some('(') => ')',
Some('[') => ']',
Some('{') => '}',
Some('<') => '>',
_ => unreachable!(),
};
if token != expected_close {
syntax_error_score += match token {
')' => 3,
']' => 57,
'}' => 1197,
'>' => 25137,
_ => unreachable!(),
};
}
}
}
Ok(syntax_error_score.to_string())
}
fn part_2(input: &str) -> Result<String> {
let mut scores = vec![];
'line_loop: for line in input.lines() {
let mut line_score: isize = 0;
let mut tokens = VecDeque::new();
for token in line.chars() {
if ['(', '[', '{', '<'].contains(&token) {
tokens.push_back(token);
continue;
}
let expected_close = match tokens.pop_back() {
Some('(') => ')',
Some('[') => ']',
Some('{') => '}',
Some('<') => '>',
_ => unreachable!(),
};
if token != expected_close {
continue 'line_loop;
}
}
for token in tokens.into_iter().rev() {
let token_score = match token {
'(' => 1,
'[' => 2,
'{' => 3,
'<' => 4,
_ => unreachable!(),
};
line_score *= 5;
line_score += token_score;
}
scores.push(line_score);
}
scores.sort();
Ok(scores[scores.len() / 2].to_string())
}