AoC_2021/src/day08.rs

94 lines
2.7 KiB
Rust

use std::collections::{BTreeSet, HashMap, HashSet};
use aoc_runner_derive::{aoc, aoc_generator};
use itertools::Itertools;
type Data = HashMap<Vec<String>, Vec<String>>;
#[aoc_generator(day08)]
pub fn input_generator(input: &str) -> Data {
// let input =
// "acedgfb cdfbe gcdfa fbcad dab cefabd cdfgeb eafb cagedb ab | cdfeb fcadb cdfeb cdbaf";
let mut ret = HashMap::new();
for line in input.lines() {
let mut line = line.split(" | ").map(|v| {
v.split(' ')
.map(|v| v.chars().sorted().collect::<String>())
.collect::<Vec<_>>()
});
ret.insert(line.next().unwrap(), line.next().unwrap());
}
ret
}
fn resolve_overlaps(digits: &HashMap<BTreeSet<char>, HashSet<u8>>) -> HashMap<BTreeSet<char>, u8> {
todo!()
}
fn unshuffle(input: &[String], output: &[String]) -> usize {
let mut results: HashMap<BTreeSet<char>, u8> = HashMap::new();
// segments -> candidate digits
let mut digits: HashMap<BTreeSet<char>, HashSet<u8>> = HashMap::new();
// 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 digits
// 6, 2, 5, 5, 4, 5, 6, 3, 7, 6 segments
// println!("Unshuffling: {:?} -> {:?}", input, output);
// LHS is sub-pattern of RHS
let overlap: HashMap<u8,Vec<u8>> = HashMap::from([
(0,vec![8]),
(1,vec![3,4,7,8,9]),
(2,vec![8]),
]);
for val in input {
let candidates: Vec<u8> = match val.len() {
2 => vec![1],
3 => vec![7],
4 => vec![4],
5 => vec![2, 5, 3],
6 => vec![6, 9],
7 => vec![8],
_ => unreachable!(),
};
digits
.entry(val.chars().collect())
.or_default()
.extend(&candidates);
}
for _ in 0..10 {
// println!("===================");
// println!("D: {:?}", digits);
// println!("R: {:?}", results);
if results.len() == 10 {
break;
}
for (k, v) in &digits {
if v.len() == 1 {
let c = v.iter().copied().next().unwrap();
results.insert(k.clone(), c);
}
}
digits.values_mut().for_each(|v| {
for c in results.values() {
v.remove(c);
}
});
digits = digits.drain().filter(|(_, v)| !v.is_empty()).collect();
}
return 0;
}
#[aoc(day08, part1)] // 310
pub fn solve_part1(input: &Data) -> usize {
input
.values()
.flatten()
.filter(|v| {
[2, 4, 3, 7].contains(&v.len())
})
.count()
}
#[aoc(day08, part2)]
pub fn solve_part2(input: &Data) -> usize {
input.iter().map(|(k, v)| unshuffle(k, v)).sum()
}