04.rs
1 #![feature(test)] 2 3 use std::collections::VecDeque; 4 5 use rustc_hash::FxHashSet; 6 7 type Input = Vec<Card>; 8 9 #[derive(Debug)] 10 struct Card { 11 winning: FxHashSet<u32>, 12 mine: FxHashSet<u32>, 13 } 14 15 impl Card { 16 fn matches(&self) -> usize { 17 self.winning.intersection(&self.mine).count() 18 } 19 20 fn points(&self) -> usize { 21 let matches = self.matches(); 22 if matches >= 1 { 23 2usize.pow(matches as u32 - 1) 24 } else { 25 0 26 } 27 } 28 } 29 30 fn setup(input: &str) -> Input { 31 input 32 .lines() 33 .map(|line| { 34 let mut line = line.split(':').nth(1).unwrap().split('|'); 35 let mut nums = || { 36 line.next() 37 .unwrap() 38 .split_whitespace() 39 .map(|n| n.parse().unwrap()) 40 .collect() 41 }; 42 Card { 43 winning: nums(), 44 mine: nums(), 45 } 46 }) 47 .collect() 48 } 49 50 fn part1(input: &Input) -> usize { 51 input.iter().map(Card::points).sum() 52 } 53 54 fn part2(input: &Input) -> usize { 55 let mut counts = VecDeque::from(vec![1; input.len()]); 56 input 57 .iter() 58 .map(|card| { 59 let n = counts.pop_front().unwrap(); 60 counts 61 .iter_mut() 62 .take(card.matches()) 63 .for_each(|cnt| *cnt += n); 64 n 65 }) 66 .sum() 67 } 68 69 aoc::main!(2023, 4, ex: 1);