-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathstep2_eval.ts
76 lines (67 loc) · 2.06 KB
/
step2_eval.ts
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
import { read_str } from "./reader"
import { pr_str } from "./printer"
import { Mal, List, Symbol, Function, Number, Vector } from "./types"
const readline = require('readline')
const rl = readline.createInterface({
input: process.stdin,
output: process.stdout
})
function read(str: string): Mal {
return read_str(str)
}
function eval_ast(ast: Mal, repl_env: any): Mal {
if (ast instanceof Symbol) {
if (repl_env[ast.contents])
return new Function(repl_env[ast.contents])
else
throw "'" + ast.contents + "' not found"
} else if (ast instanceof List) {
return new List(ast.contents.map(x => evaluate(x, repl_env)))
} else if (ast instanceof Vector) {
return new Vector(ast.contents.map(x => evaluate(x, repl_env)))
} else {
return ast
}
}
function evaluate(ast: Mal, repl_env: any): Mal {
if (ast instanceof List) {
if (ast.contents.length == 0) {
return ast
} else {
let evaluated = eval_ast(ast, repl_env)
let fn = evaluated.contents.shift().contents
let args = evaluated.contents
let result = fn.apply(null, args.map(x => x.contents))
return read_str(result)
}
} else {
return eval_ast(ast, repl_env)
}
}
function prnt(ast: Mal): string {
return pr_str(ast)
}
function rep(str: string): void {
let repl_env = {
"+": (x: number, y: number) => x + y,
"-": (x: number, y: number) => x - y,
"*": (x: number, y: number) => x * y,
"/": (x: number, y: number) => x / y
}
try {
let ast: Mal = read(str)
let processed: Mal = evaluate(ast, repl_env)
let x: string = prnt(processed)
if (x != "")
console.log(x)
} catch (error) {
console.log(error)
}
}
// Main loop
process.stdout.write("user> ")
rl.on('line', (input: string) => {
if (input.trim() != "")
rep(input)
process.stdout.write("user> ")
});