summaryrefslogtreecommitdiff
path: root/2020/2.hs
blob: 7b83745923018005120276dd9149b5b0f7efd9e9 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
module Main where

import Text.Parsec (parse, digit, char, string, anyChar, many, many1)

import Input


data Policy = Policy Int Int Char
  deriving (Show)

parseLine :: String -> (Policy, String)
parseLine str = case parse pLine "" str of Right r -> r ; Left e -> error (show e)
  where
    pLine = do
        n1 <- read <$> many1 digit
        _ <- char '-'
        n2 <- read <$> many1 digit
        _ <- char ' '
        c <- anyChar
        _ <- string ": "
        s <- many anyChar
        return (Policy n1 n2 c, s)

valid1 :: Policy -> String -> Bool
valid1 (Policy l h c) pw =
    let count = length (filter (== c) pw)
    in l <= count && count <= h

valid2 :: Policy -> String -> Bool
valid2 (Policy l h c) pw =
    let c1 = pw !! (l - 1) ; c2 = pw !! (h - 1) in (c1 == c || c2 == c) && c1 /= c2

numValid :: (Policy -> String -> Bool) -> [(Policy, String)] -> Int
numValid f = sum . map (fromEnum . uncurry f)

main :: IO ()
main = do
    input <- map parseLine <$> getInput 2
    print (numValid valid1 input)
    print (numValid valid2 input)