Skip to content

Commit 8853761

Browse files
committed
2024_03 refactor
1 parent 5746923 commit 8853761

File tree

2 files changed

+40
-34
lines changed

2 files changed

+40
-34
lines changed

src/bin/2024_03/main.rs

Lines changed: 29 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -2,57 +2,52 @@ use aoc::common;
22
use aoc::io;
33
use itertools::Itertools;
44

5-
fn is_num(s: &str) -> bool {
6-
s.chars().all(|x| x.is_ascii_digit())
7-
}
8-
95
// the ....mul(X,Y)...... part
10-
fn solve_muls(input: &str) -> usize {
6+
fn compute(input: &str) -> usize {
117
let mut ans = 0;
12-
for pattern in io::tokenize(input, "mul(") {
13-
let tokens1 = io::tokenize(pattern, ",");
14-
let num1 = tokens1.first().unwrap();
15-
// check if num1 has all digits
16-
if is_num(num1) {
17-
let n1: usize = io::parse_num(num1);
18-
let tokens2 = io::tokenize(tokens1[1], ")");
19-
let num2 = tokens2.first().unwrap();
20-
if is_num(num2) {
21-
let n2: usize = io::parse_num(num2);
22-
ans += n1 * n2;
8+
for pattern in io::tokenize(input, "mul(").iter().skip(1) {
9+
if let Some((num1_str, num2_str_plus)) = pattern.split_once(',') {
10+
if let Some(n1) = io::try_parse_num::<usize>(num1_str) {
11+
if let Some((num2_str, _)) = num2_str_plus.split_once(')') {
12+
if let Some(n2) = io::try_parse_num::<usize>(num2_str) {
13+
ans += n1 * n2;
14+
}
15+
}
2316
}
2417
}
2518
}
2619
ans
2720
}
2821

2922
fn solve<const PART: usize>(input: &str) -> usize {
30-
let mut ans = 0;
31-
3223
if PART == 1 {
33-
ans = solve_muls(input);
24+
compute(input)
3425
} else {
35-
let indices = input
26+
let do_dont_indices = input
3627
.match_indices("do()")
3728
.chain(input.match_indices("don't()"))
38-
.sorted_by_key(|x| x.0);
29+
.sorted_by_key(|(idx, _)| *idx)
30+
.map(|(idx, do_or_dont)| {
31+
if do_or_dont == "do()" {
32+
(idx, true)
33+
} else {
34+
(idx, false)
35+
}
36+
});
3937

40-
let mut last_idx = 0;
41-
let mut yes: bool = true;
42-
for (idx, ins) in indices {
43-
if yes {
44-
ans += solve_muls(&input[last_idx..idx]);
45-
}
46-
last_idx = idx;
47-
yes = ins == "do()";
38+
let mut checkpoints = vec![(0, true)];
39+
for idx in do_dont_indices {
40+
checkpoints.push(idx);
4841
}
42+
checkpoints.push((input.len(), false));
4943

50-
if yes {
51-
ans += solve_muls(&input[last_idx..]);
52-
}
44+
checkpoints.windows(2).fold(0, |mut acc, interval| {
45+
if interval[0].1 {
46+
acc += compute(&input[interval[0].0..interval[1].0]);
47+
}
48+
acc
49+
})
5350
}
54-
55-
ans
5651
}
5752

5853
fn main() {

src/io.rs

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,17 @@ where
3737
.unwrap()
3838
}
3939

40+
#[must_use]
41+
pub fn try_parse_num<T: FromStr>(token: &str) -> Option<T>
42+
where
43+
<T as FromStr>::Err: Debug,
44+
{
45+
if token.chars().all(|x| x.is_ascii_digit() || x == '-') {
46+
return Some(parse_num(token));
47+
}
48+
None
49+
}
50+
4051
#[must_use]
4152
pub fn line_batches(input: &str) -> Vec<Vec<&str>> {
4253
input

0 commit comments

Comments
 (0)