Browse Source

Fix copying and comparing of some classes

tags/gm/2021-09-23T00Z/github.com--lark-parser-lark/0.11.3
Gary Geng 4 years ago
parent
commit
83ce0c7a00
3 changed files with 32 additions and 1 deletions
  1. +22
    -0
      lark/lexer.py
  2. +1
    -1
      lark/parsers/lalr_parser.py
  3. +9
    -0
      tests/test_parser.py

+ 22
- 0
lark/lexer.py View File

@@ -186,6 +186,13 @@ class LineCounter:
self.column = 1 self.column = 1
self.line_start_pos = 0 self.line_start_pos = 0


def __eq__(self, other):
if not isinstance(other, LineCounter):
return False
return (self.newline_char == other.newline_char and self.char_pos == other.char_pos
and self.line == other.line and self.column == other.column
and self.line_start_pos == other.line_start_pos)

def feed(self, token, test_newline=True): def feed(self, token, test_newline=True):
"""Consume a token and calculate the new line & column. """Consume a token and calculate the new line & column.


@@ -405,6 +412,13 @@ class LexerState:
self.line_ctr = line_ctr self.line_ctr = line_ctr
self.last_token = last_token self.last_token = last_token


def __eq__(self, other):
if not isinstance(other, LexerState):
return False

return (self.text == other.text and self.line_ctr == other.line_ctr
and self.last_token == other.last_token)

def __copy__(self): def __copy__(self):
return type(self)(self.text, copy(self.line_ctr), self.last_token) return type(self)(self.text, copy(self.line_ctr), self.last_token)


@@ -465,4 +479,12 @@ class LexerThread:


def lex(self, parser_state): def lex(self, parser_state):
return self.lexer.lex(self.state, parser_state) return self.lexer.lex(self.state, parser_state)

def __copy__(self):
copied = type(self)(
self.lexer,
''
)
copied.state = copy(self.state)
return copied
###} ###}

+ 1
- 1
lark/parsers/lalr_parser.py View File

@@ -95,7 +95,7 @@ class ParserState(object):
def __eq__(self, other): def __eq__(self, other):
if not isinstance(other, ParserState): if not isinstance(other, ParserState):
return False return False
return self.position == other.position
return len(self.state_stack) == len(other.state_stack) and self.position == other.position


def __copy__(self): def __copy__(self):
return type(self)( return type(self)(


+ 9
- 0
tests/test_parser.py View File

@@ -2408,9 +2408,18 @@ def _make_parser_test(LEXER, PARSER):
# Skip comma # Skip comma
return True return True
elif e.token.type == 'SIGNED_NUMBER': elif e.token.type == 'SIGNED_NUMBER':
# Make a copy and ensure it is properly made
puppet_copy = e.puppet.copy()
assert puppet_copy.parser_state == e.puppet.parser_state
assert puppet_copy.lexer_state.state == e.puppet.lexer_state.state
assert puppet_copy.parser_state is not e.puppet.parser_state
assert puppet_copy.lexer_state.state is not e.puppet.lexer_state.state
assert puppet_copy.lexer_state.state.line_ctr is not e.puppet.lexer_state.state.line_ctr

# Try to feed a comma and retry the number # Try to feed a comma and retry the number
e.puppet.feed_token(Token('COMMA', ',')) e.puppet.feed_token(Token('COMMA', ','))
e.puppet.feed_token(e.token) e.puppet.feed_token(e.token)

return True return True


# Unhandled error. Will stop parse and raise exception # Unhandled error. Will stop parse and raise exception


Loading…
Cancel
Save