module Four (four) where

import Data.List
import Data.Ord
import Data.Char
import Text.Regex.TDFA
import Debug.Trace

-- this is pretty cute actually
-- sorts and groups a string, map to tuple of char and count
-- sorts by descending count and ascending alphabet
-- then takes the first five chars
checksum :: String -> String
checksum w = snd <$> (take 5 $ sortBy (mconcat [flip $ comparing fst, comparing snd])
    ((\c -> (length c, head c)) <$> (group $ sort w)))

parse :: String -> (String, Integer, String)
parse l = (s', n', c)
    where (s:n:c:[]) = tail $ getAllTextSubmatches (l =~ "^([a-z-]*)([0-9]*)\\[([a-z]*)" :: AllTextSubmatches [] String)
          s' = filter (/= '-') s
          n' = read n

abcAdd :: (Integral a) => a -> Char -> Char
abcAdd n c = chr $ ((ord c - 97 + fromIntegral n) `mod` 26) + 97

four = do
    input <- (fmap parse) <$> lines <$> readFile "data/four.txt"

    let result1 = foldr (\(_, n, _) acc -> acc + n) 0 $ filter (\(s, _, c) -> checksum s == c) input
    putStrLn $ "part A: " ++ show result1

    let result2 = snd $ head $ filter (isPrefixOf "north" . fst) $ (\(s, n, _) -> (abcAdd n <$> s, n)) <$> input
    putStrLn $ "part B: " ++ show result2
