day 4 solution
parent
cf3d410dc7
commit
45481154d1
|
@ -0,0 +1,113 @@
|
|||
use aoc_runner_derive::{aoc, aoc_generator};
|
||||
use std::collections::HashSet;
|
||||
|
||||
#[derive(Debug)]
|
||||
struct Card {
|
||||
id: usize,
|
||||
winning: HashSet<u32>,
|
||||
present: HashSet<u32>,
|
||||
}
|
||||
|
||||
impl Card {
|
||||
fn matching_numbers(&self) -> Vec<&u32> {
|
||||
self.winning
|
||||
.intersection(&self.present)
|
||||
.collect::<Vec<&u32>>()
|
||||
}
|
||||
}
|
||||
|
||||
#[aoc_generator(day4)]
|
||||
fn parse(input: &str) -> Vec<Card> {
|
||||
input
|
||||
.lines()
|
||||
.filter_map(|line| {
|
||||
if !line.is_empty() {
|
||||
let cparts: Vec<&str> = line.split(": ").collect();
|
||||
let id = cparts[0]
|
||||
.split(" ")
|
||||
.collect::<Vec<&str>>()
|
||||
.last()?
|
||||
.trim_start()
|
||||
.parse::<usize>()
|
||||
.unwrap();
|
||||
let cnums: Vec<&str> = cparts[1].split(" | ").collect();
|
||||
let winning: HashSet<u32> = cnums[0]
|
||||
.replace(" ", " ")
|
||||
.trim_start()
|
||||
.split(" ")
|
||||
.map(|n| n.parse::<u32>().unwrap())
|
||||
.collect();
|
||||
let present: HashSet<u32> = cnums[1]
|
||||
.replace(" ", " ")
|
||||
.trim_start()
|
||||
.split(" ")
|
||||
.map(|n| n.parse::<u32>().unwrap())
|
||||
.collect();
|
||||
Some(Card {
|
||||
id,
|
||||
winning,
|
||||
present,
|
||||
})
|
||||
} else {
|
||||
None
|
||||
}
|
||||
})
|
||||
.collect()
|
||||
}
|
||||
|
||||
#[aoc(day4, part1)]
|
||||
fn part1(input: &[Card]) -> i32 {
|
||||
let mut sum = 0;
|
||||
let base: i32 = 2;
|
||||
for c in input.iter() {
|
||||
let m = c.matching_numbers();
|
||||
if m.is_empty() {
|
||||
continue;
|
||||
}
|
||||
let p = base.pow(m.len() as u32 - 1);
|
||||
if m.len() > 0 {
|
||||
sum += p;
|
||||
}
|
||||
}
|
||||
sum
|
||||
}
|
||||
|
||||
#[aoc(day4, part2)]
|
||||
fn part2(input: &[Card]) -> u32 {
|
||||
let mut cards: [u32; 202] = [1; 202];
|
||||
for i in input.len()..cards.len() {
|
||||
cards[i] = 0;
|
||||
}
|
||||
for c in input.iter() {
|
||||
let m = c.matching_numbers();
|
||||
let cur = c.id - 1;
|
||||
for i in 1..=m.len() {
|
||||
let dest = cur + i;
|
||||
if dest >= input.len() {
|
||||
continue;
|
||||
}
|
||||
cards[dest] += cards[cur];
|
||||
}
|
||||
}
|
||||
cards.iter().sum()
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::*;
|
||||
|
||||
const SAMPLE_DATA: &'static str = r#"Card 1: 41 48 83 86 17 | 83 86 6 31 17 9 48 53
|
||||
Card 2: 13 32 20 16 61 | 61 30 68 82 17 32 24 19
|
||||
Card 3: 1 21 53 59 44 | 69 82 63 72 16 21 14 1
|
||||
Card 4: 41 92 73 84 69 | 59 84 76 51 58 5 54 83
|
||||
Card 5: 87 83 26 28 32 | 88 30 70 12 93 22 82 36
|
||||
Card 6: 31 18 13 56 72 | 74 77 10 23 35 67 36 11
|
||||
"#;
|
||||
|
||||
#[test]
|
||||
fn sample_data() {
|
||||
let cards = parse(&SAMPLE_DATA);
|
||||
assert_eq!(part1(&cards), 13);
|
||||
assert_eq!(part2(&cards), 30);
|
||||
}
|
||||
}
|
|
@ -3,5 +3,6 @@ use aoc_runner_derive::aoc_lib;
|
|||
mod day01;
|
||||
mod day02;
|
||||
mod day03;
|
||||
mod day04;
|
||||
|
||||
aoc_lib! { year = 2023 }
|
||||
|
|
Loading…
Reference in New Issue