-
Notifications
You must be signed in to change notification settings - Fork 0
/
stack.cl
161 lines (150 loc) · 3.83 KB
/
stack.cl
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
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
(*
* Implementation of a simple stack machine as example of Cool language
* Command Meanings:
* - int push the integer int on the stack
* - + push a ‘+’ on the stack
* - s push an ‘s’ on the stack
* - e evaluate the top of the stack (see below)
* - d display contents of the stack
* - x stop
*)
class List {
cur: Object;
next: List;
size: Int <- 0;
push(new_cur: Object): List {
(let new_head: List <- (new List).init(cur, next) in {
size <- size + 1;
next <- new_head;
cur <- new_cur;
self;
})
};
pop(): Object {
if size = 0 then {
abort();
} else if (isvoid next) then {
size <- size - 1;
cur;
} else
(let old_cur: Object <- cur in {
size <- size - 1;
cur <- next.get_cur();
next <- next.get_next();
old_cur;
})
fi fi
};
init(new_cur: Object, new_next: List): List {
if (isvoid new_next) then {
size <- 1;
cur <- new_cur;
self;
} else {
size <- size + new_next.get_size();
cur <- new_cur;
next <- new_next;
self;
}
fi
};
get_cur(): Object {
cur
};
get_next(): List {
next
};
get_size(): Int {
size
};
};
class Stack inherits IO {
converter: A2I <- new A2I;
data: List <- new List;
push(value: Object): Stack {
{
data.push(value);
self;
}
};
pop(): Object {
data.pop()
};
size(): Int {
data.get_size()
};
print(): Object {
(let i: Int <- 0, curr_list: List <- data in {
while i < data.get_size() loop {
case curr_list.get_cur() of
str: String => out_string(str.concat("\n"));
val: Int => out_string(converter.i2a(val).concat("\n"));
obj: Object => {
abort();
1;
};
esac;
i <- i + 1;
curr_list <- curr_list.get_next();
}
pool;
})
};
};
class StackMachine {
data: Stack <- (new Stack);
converter: A2I <- (new A2I);
push(str: String): Bool {
if str = "+" then { data.push(str); true; }
else if str = "s" then { data.push(str); true; }
else if str = "d" then { data.print(); true; }
else if str = "e" then { evaluate(); true; }
else if str = "x" then false
else { data.push(converter.a2i(str)); true; }
fi fi fi fi fi
};
evaluate(): Object {
if data.size() < 3 then 0
else
(let command: Object <- data.pop() in
case command of
str: String =>
if str = "s" then
(let a: Object <- data.pop(), b: Object <- data.pop() in {
data.push(a);
data.push(b);
}
)
else if str = "+" then
(let a: Object <- data.pop(), b: Object <- data.pop() in
case a of
val1: Int =>
case b of
val2: Int => data.push(val1 + val2);
obj: Object => { abort(); };
esac;
obj: Object => { abort(); };
esac
)
else abort()
fi fi;
i: Int => push(converter.i2a(i));
obj: Object => abort();
esac
)
fi
};
};
class Main inherits IO {
converter: A2I <- new A2I;
a: StackMachine <- (new StackMachine);
main(): Object {
(let input: String <- {out_string(">"); in_string();} in {
while a.push(input) loop {
out_string(">");
input <- in_string();
}
pool;
})
};
};