#lang curly-fn racket (require "scripts/aoc.rkt") ;; solution for day 21 (define (part1 input) ; (define edges ; (for/fold ([edges '()]) ([line (in-list input)]) ; (match-define (cons ingreds allergs) line) ; (append edges (for*/list ([i (in-list ingreds)] [a (in-list allergs)]) ; (list i a))))) ; (define G (undirected-graph edges)) ;(define matching (maximum-bipartite-matching G)) (define all-ingreds (for/fold ([all (set)]) ([line (in-list input)]) (set-union all (list->set (car line))))) (define all-allergs (for/fold ([all (set)]) ([line (in-list input)]) (set-union all (list->set (cdr line))))) (define tainted (mutable-set)) (for ([allerg (in-set all-allergs)]) (define necessary (for/fold ([necessary all-ingreds]) ([line (in-list input)] #:when (member allerg (cdr line))) (set-intersect necessary (list->set (car line))))) (set-union! tainted necessary)) (define untainted (set-subtract all-ingreds tainted)) (for*/sum ([line (in-list input)] [ingred (in-list (car line))]) (if (set-member? untainted ingred) 1 0))) (define (part2 input) (define all-ingreds (for/fold ([all (set)]) ([line (in-list input)]) (set-union all (list->set (car line))))) (define all-allergs (for/fold ([all (set)]) ([line (in-list input)]) (set-union all (list->set (cdr line))))) (define tainted (mutable-set)) (for ([allerg (in-set all-allergs)]) (define necessary (for/fold ([necessary all-ingreds]) ([line (in-list input)] #:when (member allerg (cdr line))) (set-intersect necessary (list->set (car line))))) (set-union! tainted necessary)) (define tainthash (for/hash ([a (in-set all-allergs)]) (values a (for/fold ([is all-ingreds]) ([line (in-list input)] #:when (member a (cdr line))) (set-intersect is (list->set (filter #{set-member? tainted %} (car line)))))))) (define edges (for*/list ([k (in-list (hash-keys tainthash))] [v (in-set (hash-ref tainthash k))]) (list k v))) (pretty-write edges) (define G (undirected-graph edges)) (define matching (maximum-bipartite-matching G)) (displayln matching) (define mhash (for/hash ([item (in-list matching)]) (values (first item) (second item)))) (displayln mhash) (define by-allergs (sort (hash-keys mhash) stringlines fname)) (for/list ([line (in-list lines)]) (match line [(pregexp #px"^([^\\(]+) \\(contains ([^\\)]+)\\)+" (list _ p1 p2)) (define ingredients (string-split p1 " ")) (define allergens (string-split p2 ", ")) (cons ingredients allergens)] [_ (error "not shonks" line)]))) (module+ test (require rackunit) ;; tests here (displayln "no tests :(")) (module+ main (define input (parse "inputs/21")) (answer 21 1 (time (part1 input))) (answer 21 2 (time (part2 input))) (displayln "meow"))