Skip to content

Instantly share code, notes, and snippets.

@edwinb
Created January 25, 2019 14:48
Show Gist options
  • Star 10 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save edwinb/25cd0449aab932bdf49456d426960fed to your computer and use it in GitHub Desktop.
Save edwinb/25cd0449aab932bdf49456d426960fed to your computer and use it in GitHub Desktop.
Pattern matching on types
data Vect : Nat -> Type -> Type where
Nil : Vect Z t
(::) : a -> Vect k a -> Vect (S k) a
describe : Type -> String
describe Int = "Int"
describe (List t) = "List of " ++ describe t
describe (Vect n t) = "Vect of " ++ show n ++ " " ++ describe t
describe _ = "Something else"
{-
Main> describe Int
"Int"
Main> describe Nat
"Something else"
Main> describe (Vect 10 (List Int))
"Vect of 10 List of Int"
-}
-- Not allowed, because 'a' is a parameter
-- Just as well, because the type tells us this has to be the identity function
{-
failId : a -> a
failId {a = Nat} x = x + 1
failId x = x
"typecase.blod:12:1--13:1:Attempt to match on erased argument Nat"
-}
-- 'a' isn't a parameter here (having been explicitly bound) so we can
-- match on it...
-- So we know from the type that 'notId' might not be the identity function
notId : {a : Type} -> a -> a
notId {a = Nat} x = x + 1
notId x = x
{-
Main> notId (S (S Z))
S (S (S Z))
Main> notId 94
94
-}
@shlevy
Copy link

shlevy commented Jan 25, 2019

Ah, nice, thanks!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment