diff --git a/parso/python/grammar27.txt b/parso/python/grammar27.txt index 0f7ed6f..cbee141 100644 --- a/parso/python/grammar27.txt +++ b/parso/python/grammar27.txt @@ -103,10 +103,11 @@ term: factor (('*'|'/'|'%'|'//') factor)* factor: ('+'|'-'|'~') factor | power power: atom trailer* ['**' factor] atom: ('(' [yield_expr|testlist_comp] ')' | - '[' [testlist_comp] ']' | + '[' [listmaker] ']' | '{' [dictorsetmaker] '}' | '`' testlist1 '`' | NAME | NUMBER | STRING+) +listmaker: test ( list_for | (',' test)* [','] ) testlist_comp: test ( comp_for | (',' test)* [','] ) lambdef: 'lambda' [varargslist] ':' test trailer: '(' [arglist] ')' | '[' subscriptlist ']' | '.' NAME @@ -127,8 +128,12 @@ arglist: (argument ',')* (argument [','] # results in an ambiguity. ast.c makes sure it's a NAME. argument: test [comp_for] | test '=' test +list_iter: list_for | list_if +list_for: 'for' exprlist 'in' testlist_safe [list_iter] +list_if: 'if' old_test [list_iter] + comp_iter: comp_for | comp_if -comp_for: 'for' exprlist 'in' testlist_safe [comp_iter] +comp_for: 'for' exprlist 'in' or_test [comp_iter] comp_if: 'if' old_test [comp_iter] testlist1: test (',' test)* diff --git a/parso/python/parser.py b/parso/python/parser.py index b05944f..92ac314 100644 --- a/parso/python/parser.py +++ b/parso/python/parser.py @@ -38,6 +38,10 @@ class Parser(BaseParser): 'while_stmt': tree.WhileStmt, 'try_stmt': tree.TryStmt, 'comp_for': tree.CompFor, + # Not sure if this is the best idea, but IMO it's the easiest way to + # avoid extreme amounts of work around the subtle difference of 2/3 + # grammar in list comoprehensions. + 'list_for': tree.CompFor, 'decorator': tree.Decorator, 'lambdef': tree.Lambda, 'old_lambdef': tree.Lambda, @@ -101,6 +105,12 @@ class Parser(BaseParser): # ones and therefore have pseudo start/end positions and no # prefixes. Just ignore them. children = [children[0]] + children[2:-1] + elif symbol == 'list_if': + # Make transitioning from 2 to 3 easier. + symbol = 'comp_if' + elif symbol == 'listmaker': + # Same as list_if above. + symbol = 'testlist_comp' return self.default_node(symbol, children) def convert_leaf(self, pgen_grammar, type, value, prefix, start_pos):