Last active
October 4, 2019 00:06
-
-
Save JakobBruenker/42b35d27c025b6d286b0090461158fc4 to your computer and use it in GitHub Desktop.
variadic listof
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
{-# LANGUAGE TypeFamilies #-} | |
{-# LANGUAGE MultiParamTypeClasses #-} | |
{-# LANGUAGE FunctionalDependencies #-} | |
{-# LANGUAGE FlexibleInstances #-} | |
module ListOf where | |
-- was a closed type family at first, but jle` said it might be cleaner to put | |
-- it inside the class, and I agree | |
class ListOfable t where | |
type Elem t | |
listOfWithAcc :: (e ~ Elem t) => [e] -> t | |
instance ListOfable [a] where | |
type Elem [a] = a | |
listOfWithAcc acc = reverse acc | |
instance (ListOfable t, Elem t ~ a) => ListOfable (a -> t) where | |
type Elem (a -> t) = a | |
listOfWithAcc acc x = listOfWithAcc (x:acc) | |
listOf :: ListOfable t => t | |
listOf = listOfWithAcc [] | |
------------------------------------------------------------------------------- | |
-- with help from jle` | |
class ListOfable' a t | t -> a where | |
listOfWithAcc' :: [a] -> t | |
instance ListOfable' a [a] where | |
listOfWithAcc' acc = reverse acc | |
instance ListOfable' a t => ListOfable' a (a -> t) where | |
listOfWithAcc' acc x = listOfWithAcc' (x:acc) | |
listOf' :: ListOfable' a t => t | |
listOf' = listOfWithAcc' [] | |
------------------------------------------------------------------------------- | |
main :: IO () | |
main = do printList $ listOf 1 2 3 | |
printList (listOf :: [Bool]) | |
printList $ listOf "Hello" "World" | |
printList $ listOf False True False True | |
printList $ listOf (Just 4) (Just 3) Nothing Nothing (Just 2) | |
putStrLn "--------------" | |
printList $ listOf' 1 2 3 | |
printList (listOf' :: [Bool]) | |
printList $ listOf' "Hello" "World" | |
printList $ listOf' False True False True | |
printList $ listOf' (Just 4) (Just 3) Nothing Nothing (Just 2) | |
where printList :: Show a => [a] -> IO () | |
printList = print |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment