-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathparser.py
More file actions
112 lines (95 loc) · 2.95 KB
/
Copy pathparser.py
File metadata and controls
112 lines (95 loc) · 2.95 KB
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
#!/usr/bin/python
# -*- coding: utf-8 -*-
from lexer import Lexer
class SyntaxError(Exception):
def __init__(self, *args):
self.args = args
def __repr__(self):
return ''.join([i for i in self.args])
class Parser:
def __init__(self, _input, k=1):
self._input = Lexer(_input)
self.k = k
self.p = 0
self.look_ahead = []
for i in range(k):
token = self._input.next_token()
self.look_ahead.append(token)
self.p = (self.p + 1) % self.k
def consume(self):
token = self.look_ahead[self.p]
self.look_ahead[self.p] = self._input.next_token()
self.p = (self.p + 1) % self.k
return token
def lt(self, i):
token = self.look_ahead[(self.p + i - 1) % self.k]
return token
def la(self, i=1):
token = self.lt(i)
return token.type
def match(self, token_type):
_type = self.la()
if _type == token_type:
return True
return False
def object(self):
if self.match(Lexer.L_PARENTHESES):
if self.match(Lexer.R_PARENTHESES):
self.consume()
return {}
else:
mem = self.members()
self.match(Lexer.R_PARENTHESES)
self.consume()
return mem
def members(self):
d = {}
d.update(self.pair())
if self.match(Lexer.COMMA):
self.consume()
d.update(self.members())
return d
def pair(self):
if self.match(Lexer.STRING):
token = self.consume()
key = token.val
if self.match(Lexer.COLON):
self.consume()
val = self.value()
return {key: val}
else:
raise SyntaxError('Key must be string.')
def value(self):
if self.match(Lexer.STRING):
val = self.consume().val
elif self.match(Lexer.NUMBER):
val = self.consume().val
elif self.match(Lexer.TRUE):
val = self.consume().val
elif self.match(Lexer.FALSE):
val = self.consume().val
elif self.match(Lexer.NULL):
val = self.consume().val
elif self.match(Lexer.L_PARENTHESES):
val = self.object()
elif self.match(Lexer.L_BRACKETS):
val = self.array()
return val
def array(self):
if self.match(Lexer.L_BRACKETS):
self.consume()
if self.match(Lexer.R_BRACKETS):
self.consume()
return []
else:
val = self.elements()
if self.match(Lexer.R_BRACKETS):
self.consume()
return val
def elements(self):
elem = []
elem.append(self.value())
if self.match(Lexer.COMMA):
self.consume()
elem.extend(self.elements())
return elem