Sfoglia il codice sorgente

an evaluator for the language from chapter 3 of tapl

Lucas Stadler 10 anni fa
parent
commit
fa98492613
1 ha cambiato i file con 59 aggiunte e 0 eliminazioni
  1. 59 0
      hs/tapl/Arith.hs

+ 59 - 0
hs/tapl/Arith.hs

@ -0,0 +1,59 @@
1
-- An evaluator for the untyped calculus of booleans and numbers, as
2
-- presented in chapter 3 of Types and Programming Languages.
3
module Arith where
4
5
import Prelude hiding (pred, succ)
6
7
data Expr = ATrue
8
          | AFalse
9
          | AIfThenElse Expr Expr Expr
10
          | AZero
11
          | ASucc Expr
12
          | APred Expr
13
          | AIsZero Expr
14
          deriving (Show)
15
16
true, false :: Expr
17
true  = ATrue
18
false = AFalse
19
20
ifthenelse :: Expr -> Expr -> Expr -> Expr
21
ifthenelse = AIfThenElse
22
23
zero :: Expr
24
zero = AZero
25
26
succ, pred :: Expr -> Expr
27
succ = ASucc
28
pred = APred
29
30
iszero :: Expr -> Expr
31
iszero = AIsZero
32
33
eval :: Expr -> Expr
34
eval ATrue = ATrue
35
eval AFalse = AFalse
36
eval (AIfThenElse test thenExpr elseExpr) =
37
    case eval test of
38
        ATrue -> eval thenExpr
39
        AFalse -> eval elseExpr
40
        _ -> error "test must return true or false"
41
eval AZero = AZero
42
eval (ASucc e) =
43
    case eval e of
44
        AZero -> ASucc AZero
45
        (ASucc f) -> ASucc f
46
        (APred f) -> f
47
        _ -> error "succ must operate on a number"
48
eval (APred e) =
49
    case eval e of
50
        AZero -> APred AZero
51
        (ASucc f) -> f
52
        (APred f) -> APred f
53
        _ -> error "pred must operate on a number"
54
eval (AIsZero e) =
55
    case eval e of
56
        AZero -> ATrue
57
        (ASucc _) -> AFalse
58
        (APred _) -> AFalse
59
        _ -> error "iszero must operate on a number"