fork download
  1. {-# LANGUAGE GADTs #-}
  2.  
  3. import Control.Arrow
  4. import Data.Function
  5.  
  6. data Sized a where
  7. Unit :: Sized ()
  8. Int :: Sized Int
  9. Char :: Sized Char
  10. Sum :: Sized a -> Sized b -> Sized (Either a b)
  11. Prod :: Sized a -> Sized b -> Sized (a, b)
  12. Iso :: Sized a -> (b -> a) -> Sized b
  13.  
  14. size :: Sized a -> a -> Int
  15. size Unit = const 0
  16. size Int = const 1
  17. size Char = const 1
  18. size (Sum f g) = size f ||| size g
  19. size (Prod f g) = size f *** size g >>> uncurry (+)
  20. size (Iso f g) = size f . g
  21.  
  22. conv [] = Left ()
  23. conv (x:xs) = Right (x, xs)
  24.  
  25. list x = fix $ \y -> Iso (Sum Unit $ Prod x y) conv
  26.  
  27. main = print $ list Int `size` [1..5]
Success #stdin #stdout 0s 6264KB
stdin
Standard input is empty
stdout
5