-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathlisp_parser.py
51 lines (47 loc) · 1.18 KB
/
lisp_parser.py
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
# Lisp tokenizer and parser
def tokenize(content: str):
token = ''
skip_line = False
for ch in content:
if skip_line and ch in "\r\n":
skip_line = False
continue
if ch in " \t\r\n":
if len(token) > 0:
yield token
token = ''
continue
elif skip_line:
continue
elif ch in "#":
skip_line = True
continue
elif ch in "()[]{}":
if len(token) > 0:
yield token
token = ''
yield ch
continue
else:
token += ch
if len(token) > 0:
yield token
yield None
def parse(content: str):
sexp = []
stack = []
tokenizer = tokenize(content)
while True:
token = next(tokenizer)
if token is None:
break
elif token in "([{":
stack.append(sexp)
sexp = []
elif token in ")]}":
temp = sexp
sexp = stack.pop()
sexp.append(temp)
else:
sexp.append(token)
return sexp