summaryrefslogtreecommitdiff
path: root/assignment-8/skeleton8.icl
blob: 3e81cceaa6f19709678ec9d8dc0f25c6f19c770a (plain) (blame)
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
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
module skeleton8

/**
 * Advanved Progrmming 2017, Assignment 8
 * Pieter Koopman, pieter@cs.ru.nl
 */

import StdList
import StdString

import Control.Applicative
import Control.Monad
from Control.Monad.State import :: StateT(StateT),
	instance Functor (StateT s m), instance Applicative (StateT s m), instance Monad (StateT s m),
	gets, modify
import Data.Error
from Data.Func import $
import Data.Functor
import qualified Data.Map as Map
import Data.Maybe
from Text import <+

from iTasks import class iTask, class toPrompt, class Publishable, instance Publishable Task,
	instance toPrompt String, instance Functor Task,
	class TApplicative, instance TApplicative Task,
	generic gEq, generic gDefault, generic JSONDecode, generic JSONEncode, generic gText, generic gEditor,
	:: JSONNode, :: TextFormat, :: Editor, :: TaskValue(..), :: Stability, :: Task, :: Action,
	:: TaskCont(..), :: ViewOption(..), :: UpdateOption(..),
	-||-, -||, ||-, >>*, always, hasValue, updateInformation, viewInformation, startEngine
import qualified iTasks
import qualified iTasks.WF.Combinators.Overloaded as WF

(>>>=)     :== 'iTasks'.tbind
(>>>|) a b :== 'iTasks'.tbind a (\_ -> b)
treturn    :== 'iTasks'.return
ActionOk   :== 'iTasks'.ActionOk
ActionQuit :== 'iTasks'.ActionQuit
ActionNew  :== 'iTasks'.ActionNew

:: Expression
	= New      [Int]
	| Elem     Int
	| Variable Ident
	| Size     Set
	| (+.) infixl 6 Expression Expression
	| (-.) infixl 6 Expression Expression
	| (*.) infixl 7 Expression Expression
	| (=.) infixl 2 Ident Expression

:: Logical
	= TRUE | FALSE
	| (In) infix 4 Elem Set
	| (==.) infix 4 Expression Expression
	| (<=.) infix 4 Expression Expression
	| Not Logical
	| (||.) infixr 2 Logical Logical
	| (&&.) infixr 3 Logical Logical

:: Stmt
	= If Logical Stmt Stmt
	| For Ident Set Stmt
	| Expression Expression
	| Logical Logical

:: Set   :== Expression
:: Elem  :== Expression
:: Ident :== String

// === State

:: Val
	= VElem Int
	| VSet  [Int]

:: State :== 'Map'.Map Ident Val

:: Sem a :== StateT State (MaybeError String) a
// Or define :: Sem a = Sem (s -> MaybeErrorString (a,s)) and copy the relevant
// instances from Control.Monad.State

store :: Ident Val -> Sem Val
store i v = modify ('Map'.put i v) $> v

read :: Ident -> Sem Val
read i = gets ('Map'.get i) >>= \v -> case v of
	Nothing -> fail $ "unknown variable '" <+ i <+ "'"
	Just v  -> pure v

fail :: String -> Sem a
fail e = StateT \_ -> Error e

eval :: Expression -> Sem Val
eval (New xs) = pure $ VSet  xs
eval (Elem x) = pure $ VElem x
eval (Variable i) = read i
eval (Size s)     = eval s >>= \xs -> case xs of
	VSet xs -> pure $ VElem $ length xs
	_       -> fail "Size :: Set -> Elem applied to Elem"
//eval (a +. b) TODO

// === semantics


// === simulation

Start = ()