-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathcore_interpE.hs
73 lines (61 loc) · 1.78 KB
/
core_interpE.hs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
module CoreInterp where
import ErrorMonad
type Name = String
data Term = Var Name
| ConI Int
| ConS String
| ConC Char
| ConL [Value]
| Add Term Term
| Cat Term Term
| Lam Name Term
| App Term Term
data Value = Num Int
| Str String
| Ch Char
| List [Value]
| Fun (Value -> E Value)
instance Show Value where
show (Num n) = show n
show (Str s) = show s
show (Ch c) = show c
show (List l) = show l
show (Fun f) = "<function>"
type Environment = [(Name, Value)]
interp :: Term -> Environment -> E Value
interp (Var x) e = look_up x e
interp (ConI i) e = return (Num i)
interp (ConS s) e = return (Str s)
interp (ConC c) e = return (Ch c)
interp (ConL l) e = return (List l)
interp (Add u v) e = do
a <- interp u e
b <- interp v e
add a b
interp (Lam x v) e = return (Fun (\a -> interp v ((x,a):e)))
interp (App t u) e = do
f <- interp t e
a <- interp u e
apply f a
interp (Cat u v) e = do
s1 <- interp u e
s2 <- interp v e
cat s1 s2
look_up :: Name -> Environment -> E Value
look_up x [] = errorE ("variable not in scope: " ++ x)
look_up x ((y,b):e) = if x == y
then return b
else look_up x e
add :: Value -> Value -> E Value
add (Num i) (Num j) = return (Num (i + j))
add a b = errorE ("should be numbers: " ++ show a ++ ", " ++ show b)
apply :: Value -> Value -> E Value
apply (Fun k) a = k a
apply f a = errorE ("should be function: " ++ show f)
cat :: Value -> Value -> E Value
cat (Str s1) (Str s2) = return (Str (s1 ++ s2))
cat (List l1) (List l2) = return (List (l1 ++ l2))
cat a b = errorE ("should either be both strings or both lists: " ++ show a ++ ", " ++ show b)
t1 = do
x <- interp (Var "me") [("me", (Num 21))]
interp (Cat (ConL [x, (Num 3)]) (ConL [(Num 1), (Num 20)])) []