Dipping my toe into the waters of dependent types, I had a crack at the canonical \"list with statically-typed length\" example.
{-# LANGUAGE DataKinds, GADT
In
fromList :: [a] -> SafeList n a
n
is universally quantified -- i.e. this signature is claiming that we should be able to build a SafeList
of any length from the list. Instead you want to quantify existentially, which can only be done by defining a new data type:
data ASafeList a where
ASafeList :: SafeList n a -> ASafeList a
Then your signature should be
fromList :: [a] -> ASafeList a
You can use it by pattern matching on ASafeList
useList :: ASafeList a -> ...
useList (ASafeList xs) = ...
and in the body, xs
will be a SafeList n a
type with an unknown (rigid) n
. You will probably have to add more operations to use it in any nontrivial way.