1 {-# OPTIONS_GHC -fno-warn-unused-do-bind -fno-warn-orphans #-}
2 {-# LANGUAGE OverloadedStrings #-}
6 -- Copyright : Tomáš Musil 2014
9 -- Maintainer : tomik.musil@gmail.com
10 -- Stability : experimental
12 -- Parser for Hindley-Milner terms and types.
19 import Data.Text as T hiding (map)
20 import Data.Attoparsec.Text
21 import Control.Applicative
24 import qualified Lambda.Parser.Fancy as Lambda
25 import qualified Lambda.Term as Lambda
27 braced :: String -> String
28 braced t = "(" ++ t ++ ")"
30 instance Show Term where
32 show (Lam x (NTTerm (Lam y t))) = show (Lam (x ++ " " ++ y) t)
33 show (Lam x t) = braced $ "λ" ++ x ++ "." ++ show t
34 show (App a (NTTerm (App b c))) = show a ++ " " ++ (braced $ show (App b c))
35 show (App t r) = show t ++ " " ++ show r
36 show (Let x e1 e2) = braced $ "let " ++ x ++ " = " ++ show e1 ++ " in " ++ show e2
38 instance Show TypedTerm where
39 show (NTTerm t) = show t
40 show (TTerm t tp) = braced $ show t ++ " :: " ++ show tp
42 instance Show Type where
43 show (Primitive t) = t
45 show (TypeFunction a b) = braced $ show a ++ " -> " ++ show b
47 instance Show TypeScheme where
48 show (TScheme t) = show t
49 show (TSForAll x t) = braced $ "∀" ++ x ++ ": " ++ show t
51 tRead :: String -> Term
54 parseTerm :: Parser TypedTerm
55 parseTerm = parseLet <|>
56 (lambdaToHM <$> Lambda.parseTerm)
58 parseLet :: Parser TypedTerm
62 (Lambda.Var x) <- Lambda.parseVar
64 e1 <- lambdaToHM <$> Lambda.parseTerm
66 e2 <- lambdaToHM <$> Lambda.parseTerm
68 return . NTTerm $ Let x e1 e2
70 lambdaToHM :: Lambda.Term -> TypedTerm
71 lambdaToHM (Lambda.Var x) = NTTerm $ Var x
72 lambdaToHM (Lambda.App t u) = NTTerm $ App (lambdaToHM t) (lambdaToHM u)
73 lambdaToHM (Lambda.Lambda x t) = NTTerm $ Lam x (lambdaToHM t)
76 -- TODO prop> t == tRead (show (t :: Term))
79 tRead :: String -> Term
80 tRead s = case parseOnly (parseTerm <* endOfInput) (T.pack s) of