--- |
--- prop> t == tRead (show (t :: Term))
-
-tRead :: String -> Term
-tRead s = case parseOnly (parseTerm <* endOfInput) (T.pack s) of
- (Right t) -> t
- (Left e) -> error e
-
-parseVar :: Parser Term
-parseVar = do
- x <- many1 (letter <|> digit)
- return $! Var x
-
-parseLambda :: Parser Term
-parseLambda = do
- char '\\' <|> char 'λ'
- vars <- sepBy1 parseVar (char ' ')
- char '.'
- t <- parseTerm
- return $! createLambda vars t
-
-createLambda :: [Term] -> Term -> Term
-createLambda (Var x : vs) t = Lambda x $ createLambda vs t
-createLambda [] t = t
-createLambda _ _ = error "createLambda failed"
-
-parseApp :: Parser Term
-parseApp = do
- aps <- sepBy1 (parseBraces <|> parseLambda <|> parseVar) (char ' ')
- return $! createApp aps
-
-createApp :: [Term] -> Term
-createApp [t] = t
-createApp (t:ts:tss) = createApp (App t ts : tss)
-createApp [] = error "empty createApp"
-
-parseBraces :: Parser Term
-parseBraces = do
- char '('
- t <- parseTerm
- char ')'
- return t
-
-parseTerm :: Parser Term
-parseTerm = parseApp <|>
- parseBraces <|>
- parseLambda <|>
- parseVar
-
--------------------------------------------------
+alphaNorm :: Term -> Term
+alphaNorm = alpha varnames
+ where
+ alpha (v:vs) (Lambda x r) = Lambda v . alpha vs $ substitute x (Var v) r
+ alpha vs (App u v) = App (alpha vs u) (alpha vs v)
+ alpha _ (Var x) = Var x
+ alpha [] _ = undefined