Advertisement
tamarin_vs19

Untitled

Dec 11th, 2020 (edited)
243
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. import Data.List
  2. type Symb = String
  3.    
  4. infixl 2 :@
  5. infix 1 `alphaEq`
  6.  
  7. data Expr = Var Symb
  8.           | Expr :@ Expr
  9.           | Lam Symb Expr
  10.           deriving (Eq, Read, Show)
  11.  
  12. subst :: Symb -> Expr -> Expr -> Expr
  13. subst v n m@(Var x) | v == x = n
  14.   | otherwise = m
  15. subst v n (a :@ b) = (subst v n a) :@ (subst v n b)
  16. subst v n m@(Lam x term) | x == v = m
  17.   | x `notElem` freeVars n = Lam x $ subst v n term
  18.   | otherwise = subst v n $ Lam z (subst x (Var z) term)   
  19.   where
  20.     z = freshVar (allVars n `union` allVars m) "new"
  21.  
  22. alphaEq :: Expr -> Expr -> Bool
  23. alphaEq (Var x) (Var y) = x == y
  24. alphaEq (a :@ b) (c :@ d) = alphaEq a c && alphaEq b d
  25. alphaEq (Lam x n) (Lam y m) = alphaEq n (subst y (Var x) m)
  26. alphaEq _ _ = False
  27.  
  28.  
  29. freeVars :: Expr -> [Symb]
  30. freeVars (Var v) = [v]
  31. freeVars (a :@ b) = freeVars a `union` freeVars b
  32. freeVars (Lam v e) = freeVars e \\ [v]
  33.  
  34. boundVars :: Expr -> [Symb]
  35. boundVars (Var v) = []
  36. boundVars (a :@ b) = freeVars a `union` freeVars b
  37. boundVars (Lam v e) = (freeVars e) `union` [v]
  38.  
  39. allVars :: Expr -> [Symb]
  40. allVars e = freeVars e `union` boundVars e
  41.  
  42. freshVar :: [Symb] -> String -> Symb
  43. freshVar [] s = s
  44. freshVar (l:ls) s =
  45.   if l == s
  46.   then freshVar ls (s ++ "_" ++ l)
  47.   else freshVar ls s
  48.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement