Strictness annotations on type parameters
Ralf Hinze
ralf at informatik.uni-bonn.de
Wed Dec 7 04:43:33 EST 2005
> It's hard to avoid the feeling that one ought to be able to say
> something useful about strictness in the types but it's swampy
> territory, and hard to get right.
Fortunately, it's easy to dry up the `swampy territory'. The type
`Contract' below models strictness requirements. The function
`assert' implements them (`assert c' is a so-called projection).
Feel free to experiment with different designs ...
> {-# OPTIONS -fglasgow-exts #-}
> infixr :->
>
> data Contract :: * -> * where
> Id :: Contract a
> (:->) :: Contract a -> Contract b -> Contract (a -> b)
> (:=>) :: Contract a -> Contract b -> Contract (a -> b)
> List :: Contract a -> Contract [a]
> SList :: Contract a -> Contract [a]
> assert :: Contract a -> (a -> a)
> assert Id = id
> assert (c1 :-> c2) = \ f -> assert c2 . f . assert c1
> assert (c1 :=> c2) = \ f x -> x `seq` (assert c2 . f . assert c1) x
> assert (List c) = map (assert c)
> assert (SList c) = \ xs -> eval xs `seq` map (assert c) xs
> eval [] = []
> eval (a : as) = a `seq` eval as
Some test data.
> evens [] = []
> evens [a] = [a]
> evens (a1 : a2 : as) = evens as
assert (Id :-> Id) (const 1) undefined
assert (Id :=> Id) (const 1) undefined
assert (Id :=> Id) (sum . evens) [1, undefined]
assert (SList Id :=> Id) (sum . evens) [1, undefined]
Cheers, Ralf
PS: Just in case you wonder, the code has been adopted from a recent
paper on contracts (see my homepage).
More information about the Glasgow-haskell-users
mailing list