Advertisement
nairby

AOC 2023 Day 2

Dec 2nd, 2023 (edited)
1,151
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Rust 2.50 KB | None | 0 0
  1. use std::env;
  2. use std::io::{self, prelude::*, BufReader};
  3. use std::fs::File;
  4.  
  5. extern crate regex;
  6. use regex::Regex;
  7.  
  8. const MAX_RED: usize = 12;
  9. const MAX_GREEN: usize = 13;
  10. const MAX_BLUE: usize = 14;
  11.  
  12. struct Game {
  13.     id: usize,
  14.     hands: Vec<Hand>,
  15. }
  16. impl From<&String> for Game {
  17.     fn from(s: &String) -> Self {
  18.         let re = Regex::new(r"Game (\d+): (.+)$").unwrap();
  19.         let matches = re.captures(&s).unwrap();
  20.         let hands = matches[2]
  21.             .split(";")
  22.             .map(Hand::from)
  23.             .collect::<Vec<_>>();
  24.         Game {
  25.             id: matches[1].parse().unwrap(),
  26.             hands: hands,
  27.         }
  28.     }
  29. }
  30. impl Game {
  31.     pub fn is_possible(&self) -> bool {
  32.         self.hands.len() == self.hands.iter().filter(|h| h.is_valid()).count()
  33.     }
  34.     pub fn power(&self) -> usize {
  35.         self.hands.iter().map(|x| x.red  ).max().unwrap() *
  36.         self.hands.iter().map(|x| x.green).max().unwrap() *
  37.         self.hands.iter().map(|x| x.blue ).max().unwrap()
  38.     }
  39. }
  40.  
  41. struct Hand {
  42.     red: usize,
  43.     green: usize,
  44.     blue: usize,
  45. }
  46. impl Hand {
  47.     pub fn is_valid(&self) -> bool {
  48.         self.red <= MAX_RED && self.green <= MAX_GREEN && self.blue <= MAX_BLUE
  49.     }
  50. }
  51. impl From<&str> for Hand {
  52.     fn from(s: &str) -> Self {
  53.         Hand {
  54.             red:   cubes_for_color("red",  &s),
  55.             green: cubes_for_color("green",&s),
  56.             blue:  cubes_for_color("blue", &s),
  57.         }
  58.     }
  59. }
  60.  
  61. fn cubes_for_color(color: &str, hand: &str) -> usize {
  62.     let re = format!(r"(\d+) {color}");
  63.     let re_color = Regex::new(&re).unwrap();
  64.     if let Some(matches) = re_color.captures(hand) {
  65.         return matches[1].parse().unwrap();
  66.     }
  67.     0
  68. }
  69.  
  70. fn solve(input: &str) -> io::Result<()> {
  71.     let file = File::open(input).expect("Input file not found.");
  72.     let reader = BufReader::new(file);
  73.  
  74.     // Input
  75.     let input: Vec<String> = match reader.lines().collect() {
  76.         Err(err) => panic!("Unknown error reading input: {}", err),
  77.         Ok(result) => result,
  78.     };
  79.  
  80.     let games: Vec<_> = input.iter().map(Game::from).collect();
  81.     let part1: usize = games.iter().filter(|x| x.is_possible()).map(|g| g.id).sum();
  82.  
  83.     println!("Part 1: {part1}"); // 2369
  84.  
  85.     let part2: usize = games.iter().map(|g| g.power()).sum();
  86.     println!("Part 2: {part2}"); // 66363
  87.  
  88.     Ok(())
  89. }
  90.  
  91. fn main() {
  92.     let args: Vec<String> = env::args().collect();
  93.     let filename = &args[1];
  94.     solve(&filename).unwrap();
  95. }
  96.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement