-
Notifications
You must be signed in to change notification settings - Fork 0
/
UData.hs
79 lines (71 loc) · 4.25 KB
/
UData.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
74
75
76
77
78
79
module UData where
data BNum = BInt Int | BFloat Double deriving Show
data BBinaryArith = BAdd | BSub | BMul | BDiv | BMod deriving Show
data BArith = BArith2 BBinaryArith BNum | BToInt | BToFloat deriving Show
data BFunc = BArithFunc BArith | BArith2Func BBinaryArith deriving Show
data BValue = BNumVal BNum | BFuncVal BFunc | BIntList [Int] deriving Show
data BResult = BClean BValue | BException [Char] deriving Show
numToBResult :: BNum -> BResult
numToBResult a = BClean (BNumVal a)
data BCompType = BLe | BGe | BNLe | BNGe | BEq | BNEq deriving Show
applyBVal :: BValue -> BValue -> BResult
applyBVal (BFuncVal b) (BNumVal v) = applyBFunc b v
applyBVal (BFuncVal b) _ = BException ("cannot apply non-numeric argument to builtin function "++(show b))
applyBVal (BIntList args) (BNumVal (BInt v)) = BClean (BIntList (v:args))
applyBVal (BIntList args) _ = BException "cannot append non-integer number in IntList"
applyBVal _ _ = BException "cannot use numeric value as function"
applyBFunc :: BFunc -> BNum -> BResult
applyBFunc (BArith2Func a) d = BClean (BFuncVal (BArithFunc (BArith2 a d)))
applyBFunc (BArithFunc a) v = applyBArith a v
applyBArith :: BArith -> BNum -> BResult
applyBArith (BArith2 a b) c = applyBBinaryArith a b c
applyBArith BToInt (BInt a) = numToBResult (BInt a)
applyBArith BToInt (BFloat a) = numToBResult (BInt (floor a))
applyBArith BToFloat (BFloat a) = numToBResult (BFloat a)
applyBArith BToFloat (BInt a) = numToBResult (BFloat (fromIntegral a))
applyBBinaryArith :: BBinaryArith -> BNum -> BNum -> BResult
applyBBinaryArith BAdd (BInt a) (BInt b) = numToBResult (BInt (a+b))
applyBBinaryArith BAdd (BFloat a) (BInt b) = numToBResult (BFloat (a+(fromIntegral b)))
applyBBinaryArith BAdd (BInt a) (BFloat b) = numToBResult (BFloat ((fromIntegral a)+b))
applyBBinaryArith BAdd (BFloat a) (BFloat b) = numToBResult (BFloat (a+b))
applyBBinaryArith BSub (BInt a) (BInt b) = numToBResult (BInt (a-b))
applyBBinaryArith BSub (BFloat a) (BInt b) = numToBResult (BFloat (a-(fromIntegral b)))
applyBBinaryArith BSub (BInt a) (BFloat b) = numToBResult (BFloat ((fromIntegral a)-b))
applyBBinaryArith BSub (BFloat a) (BFloat b) = numToBResult (BFloat (a-b))
applyBBinaryArith BMul (BInt a) (BInt b) = numToBResult (BInt (a*b))
applyBBinaryArith BMul (BFloat a) (BInt b) = numToBResult (BFloat (a*(fromIntegral b)))
applyBBinaryArith BMul (BInt a) (BFloat b) = numToBResult (BFloat ((fromIntegral a)*b))
applyBBinaryArith BMul (BFloat a) (BFloat b) = numToBResult (BFloat (a*b))
applyBBinaryArith BDiv _ (BInt 0) = BException "divided by zero"
applyBBinaryArith BDiv (BInt a) (BInt b) = numToBResult (BInt (a `div`b))
applyBBinaryArith BDiv (BFloat a) (BInt b) = numToBResult (BFloat (a/(fromIntegral b)))
applyBBinaryArith BDiv (BInt a) (BFloat b) = numToBResult (BFloat ((fromIntegral a)/b))
applyBBinaryArith BDiv (BFloat a) (BFloat b) = numToBResult (BFloat (a/b))
applyBBinaryArith BMod _ (BInt 0) = BException "mod by zero"
applyBBinaryArith BMod (BInt a) (BInt b) = numToBResult (BInt (a `div`b))
applyBBinaryArith BMod _ _ = BException "cannot use non-integer value in mod"
compBNum :: BCompType -> BNum -> BNum -> Bool
compBNum BLe (BInt a) (BInt b) = (a<b)
compBNum BLe (BInt a) (BFloat b) = ((fromIntegral a)<b)
compBNum BLe (BFloat a) (BInt b) = (a<(fromIntegral b))
compBNum BLe (BFloat a) (BFloat b) = (a<b)
compBNum BNLe (BInt a) (BInt b) = (a>=b)
compBNum BNLe (BInt a) (BFloat b) = ((fromIntegral a)>=b)
compBNum BNLe (BFloat a) (BInt b) = (a>=(fromIntegral b))
compBNum BNLe (BFloat a) (BFloat b) = (a>=b)
compBNum BGe (BInt a) (BInt b) = (a>b)
compBNum BGe (BInt a) (BFloat b) = ((fromIntegral a)>b)
compBNum BGe (BFloat a) (BInt b) = (a>(fromIntegral b))
compBNum BGe (BFloat a) (BFloat b) = (a>b)
compBNum BNGe (BInt a) (BInt b) = (a<=b)
compBNum BNGe (BInt a) (BFloat b) = ((fromIntegral a)<=b)
compBNum BNGe (BFloat a) (BInt b) = (a<=(fromIntegral b))
compBNum BNGe (BFloat a) (BFloat b) = (a<=b)
compBNum BEq (BInt a) (BInt b) = (a==b)
compBNum BEq (BInt a) (BFloat b) = ((fromIntegral a)==b)
compBNum BEq (BFloat a) (BInt b) = (a==(fromIntegral b))
compBNum BEq (BFloat a) (BFloat b) = (a==b)
compBNum BNEq (BInt a) (BInt b) = (a/=b)
compBNum BNEq (BInt a) (BFloat b) = ((fromIntegral a)/=b)
compBNum BNEq (BFloat a) (BInt b) = (a/=(fromIntegral b))
compBNum BNEq (BFloat a) (BFloat b) = (a/=b)