-
Notifications
You must be signed in to change notification settings - Fork 0
/
main.rs
79 lines (70 loc) · 2.23 KB
/
main.rs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
use std::{collections::HashSet, str::FromStr};
struct RuckSack {
items_left: HashSet<u8>,
items_right: HashSet<u8>,
}
impl RuckSack {
pub fn common_items(&self) -> Vec<u8> {
let mut res = Vec::new();
for item in &self.items_left {
if self.items_right.contains(item) {
res.push(*item);
}
}
res
}
pub fn all_items(&self) -> HashSet<u8> {
let mut res = self.items_right.clone();
res.extend(self.items_left.iter().copied());
res
}
}
impl FromStr for RuckSack {
type Err = String;
fn from_str(s: &str) -> Result<Self, Self::Err> {
let chars: Vec<_> = s.chars().collect();
let (left, right) = chars.split_at(chars.len() / 2);
let value = |item: &char| {
if item.is_ascii_lowercase() {
Ok((*item as u8).saturating_sub(b'a') + 1)
} else if item.is_ascii_uppercase() {
Ok((*item as u8).saturating_sub(b'A') + 27)
} else {
Err(format!("{item} is not a valid item"))
}
};
let items_left = left.iter().map(value).collect::<Result<_, _>>()?;
let items_right = right.iter().map(value).collect::<Result<_, _>>()?;
Ok(Self {
items_left,
items_right,
})
}
}
fn main() {
let file = include_str!("../input.txt");
let rucksacks: Vec<_> = file
.lines()
.map(|line| RuckSack::from_str(line).unwrap())
.collect();
// Part 1
let common_items: Vec<_> = rucksacks.iter().flat_map(RuckSack::common_items).collect();
let sum: u32 = common_items.iter().copied().map(u32::from).sum();
println!("Part 1: Common items sum: {sum}");
// Part 2
let sum: u32 = rucksacks
.chunks(3)
.map(|chunk| {
let [b_items, c_items] = [chunk[1].all_items(), chunk[2].all_items()];
u32::from(
chunk[0]
.all_items()
.iter()
.copied()
.find(|item| b_items.contains(item) && c_items.contains(item))
.unwrap(),
)
})
.sum();
println!("Part 2: Badges sum: {sum}");
}