handle application as list

This commit is contained in:
Rachel Lambda Samuelsson 2022-01-26 19:05:15 +01:00
parent 6499987dd8
commit 413f7d3a21
4 changed files with 49 additions and 31 deletions

View File

@ -30,10 +30,11 @@ runProcess = (fst <$>) .: runStateT
postprocess :: [H.Def] -> Process [TL]
postprocess defs = addDef <~> defs >> defToTL <~> defs
-- just adds types for processing type signatures
addDef :: H.Def -> Process ()
addDef = \case
H.VarDef _ i t _ -> lift . addEnv i =<< typeSigToPolyT t -- the type checker will check this matches the exp
H.TypeDef _ t _ -> insertType =<< fst <$> typeSigToIdParams t
H.VarDef _ i t _ -> pure ()
-- add type before typesig to id params
defToTL :: H.Def -> Process TL
@ -92,12 +93,7 @@ expToExp :: H.Exp -> Process Exp
expToExp = \case
H.ExpLet p as e -> Let p <$> assignTo2pl <~> as <*> expToExp e
H.ExpAbs p is e -> Abs p is <$> expToExp e
H.ExpApp p e1 (e2:es) -> do
e1' <- expToExp e1
e2' <- expToExp e2
es' <- traverse expToExp es
pure (foldl (App p) (App p e1' e2') es')
H.ExpApp p e [] -> throwError Oop
H.ExpApp p e es -> App p <$> expToExp e <*> expToExp <~> es
H.ExpVar p i -> pure (Var p i)
declTo2pl :: H.Decl -> Process (Id, MonoT)

View File

@ -149,29 +149,50 @@ constructs _ _ = False
infer :: Exp -> Check (Subst, MonoT)
infer = setPos >=> \case
Let _ [] e -> infer e
Let p ((i,e1):ies) e2 -> do
(s1, t1) <- infer e1
apply s1 <$> getEnv >>= \e -> localEnv e $ do
t1g <- generalize t1
addEnv i t1g
(s2, t2) <- infer (Let p ies e2)
pure (s2 <&> s1, t2)
Abs _ [] e -> infer e
Abs p (i:is) e -> localEnv' $ do
tv <- fresh
addEnv i (Forall S.empty tv)
(s, t) <- infer (Abs p is e)
pure (s, apply s tv `TArr` t)
Var _ i -> (emptySubst,) <$> lookupType i
App p e1 e2 -> localEnv' $ do
tv <- fresh
(s1, t1) <- infer e1
applyEnv s1
(s2, t2) <- infer e2
s3 <- unify (apply s2 t1) (TArr t2 tv)
return (s3 <&> s2 <&> s1, apply s3 tv)
App _ _ _ -> throwError Oop
Let _ [] e -> infer e
Let p ((i,e1):ies) e2 -> do
(s1, t1) <- infer e1
apply s1 <$> getEnv >>= \e -> localEnv e $ do
t1g <- generalize t1
addEnv i t1g
(s2, t2) <- infer (Let p ies e2)
pure (s2 <&> s1, t2)
Var _ i -> (emptySubst,) <$> lookupType i
Abs _ [] e -> infer e
Abs p (i:is) e -> localEnv' $ do
tv <- fresh
addEnv i (Forall S.empty tv)
(s, t) <- infer (Abs p is e)
pure (s, apply s tv `TArr` t)
App _ e es -> go e (reverse es)
where
go :: Exp -> [Exp] -> Check (Subst, MonoT)
go _ [] = throwError Oop
go e1 [e2] = localEnv' $ do
(s1, t1) <- infer e1
applyEnv s1
(s2, t2) <- infer e2
tv <- fresh
s3 <- unify (apply s2 t1) (t2 `TArr` tv)
pure (s3 <&> s2 <&> s1, apply s3 tv)
go e1 (e2:es) = localEnv' $ do
(s1, t1) <- go e1 es
applyEnv s1
(s2, t2) <- infer e2
tv <- fresh
s3 <- unify (apply s2 t1) (t2 `TArr` tv)
pure (s3 <&> s2 <&> s1, apply s3 tv)

View File

@ -41,7 +41,7 @@ type Exp = Exp' Pos
data Exp' a
= Let a [(Id,Exp)] Exp
| Abs a [Id] Exp
| App a Exp Exp
| App a Exp [Exp]
| Var a Id
deriving Show

1
tst Normal file
View File

@ -0,0 +1 @@
λf g x y z w. f w (g x y z)