{- Task 1 -}
namesAges = [("Felix", 45), ("Grace", 25), ("Hans", 57), ("Ivy", 25)] -- Example list for testing

bidirectionalLookup :: (Eq b, Eq a) => Either a b -> [(a, b)] -> Maybe (Either a b)
bidirectionalLookup = undefined

lengthSumMax :: (Num a, Ord a) => [a] -> (Int, a, a)
lengthSumMax = undefined

{- Task 2 -}
slice :: Int -> Int -> [a] -> [a]
slice = undefined

dropEveryNth :: Int -> [a] -> [a]
dropEveryNth = undefined

{- Task 3 -}
collatz :: Integer -> Integer
collatz = undefined

mercator :: Double -> (Double, Integer)
mercator = undefined

{- Tests -}
tests = do
    check "bidirectionalLookup1" "Just (Right 25)" (bidirectionalLookup (Left "Grace") [("Felix", 45), ("Grace", 25)])
    check "bidirectionalLookup2" "Just (Left \"Fearghal\")" (bidirectionalLookup (Right 25) [("Felix", 45), ("Fearghal", 25)])
    check "bidirectionalLookup3" "Just (Left \"Caoimhe\")" (bidirectionalLookup (Right 28) [("Caoimhe", 28), ("Eilidh", 28)])
    check "bidirectionalLookup4" "Nothing" (bidirectionalLookup (Left "Grace") ([]::[(String, Int)]))
    check "bidirectionalLookup5" "Just (Left 2)" (bidirectionalLookup (Right 0.984) [(1, 0.422), (2, 0.984), (3, 0.145)])
    check "first two elements of lengthSumMax" "(0,0)" ((\(x,y,_) -> (x,y)) $ lengthSumMax [])
    check "lengthSumMax2" "(6,10,5)" (lengthSumMax [1,0,5,1,3,0])
    check "lengthSumMax3" "(1,7,7)" (lengthSumMax [7])
    check "slice1" "\"There\"" (slice 6 10 "Hello There!")
    check "slice2" "[3,4,5]" (slice 3 5 [0..10])
    check "slice3" "[3,4,5]" (slice 3 10 [0..5])
    check "dropEveryNth1" "[]" (dropEveryNth 1 [1..5])
    check "dropEveryNth2" "[1,2,4,5,7,8,10]" (dropEveryNth 3 [1..10])
    check "dropEveryNth3" "[1,2,3,4,5]" (dropEveryNth 0 [1..5])
    check "collatz1" "0" (collatz 1)
    check "collatz2" "12" (collatz 17)
    check "collatz3" "27" (collatz 2388)
    check "mercator1" "(0.0,1)" (mercator 0)
    check "mercator2" "(0.1133286853070032,17)" (mercator 0.12)
    check "mercator3" "(0.4054651081081643,49)" (mercator 0.5)

check name e c = do
    putStr ("*** " ++ name ++ ": ")
    if show c == e then putStrLn "OK"
    else putStrLn ("ERROR; expected '" ++ e ++ "', but found '" ++ show c ++ "'")