2013-07-22 4 views
0

Я запускаю библиотеку PLY для Python на моей грамматике. Кажется, что это скомпилировано, и библиотека не предупреждает меня о каких-либо сдвигах/уменьшении или уменьшении/уменьшении ошибок. Однако запуск на очень простом примере вызывает ошибку.

копания в файл parser.out показывает, что ошибка происходит в самом конце программы:

State : 113 
Stack : DEFN ID ARROW type invariants statement . $end 
ERROR: Error : DEFN ID ARROW type invariants statement . $end 
Syntax error at: None 

где состояние 113 является:

state 113 

    (16) fn_def -> DEFN ID ARROW type invariants statement . 
    (24) tilde_loop -> statement . TILDE constant TILDE 

    SEMICOLON  reduce using rule 16 (fn_def -> DEFN ID ARROW type inva\ 
riants statement .) 
    TILDE   shift and go to state 62 

Насколько я могу сказать, анализатор следует уменьшить до fn_def.

Почему уменьшение не происходит при достижении токена $end?

(я могу вставить свою грамматику, если это поможет, хотя это может быть немного долго.)

Грамматика

Rule 0  S' -> program 
Rule 1  program -> statement_list 
Rule 2  statement -> definition SEMICOLON 
Rule 3  statement -> expression SEMICOLON 
Rule 4  statement -> control_statement 
Rule 5  statement -> compound_statement 
Rule 6  statement -> comment 
Rule 7  statement -> empty SEMICOLON 
Rule 8  statement_list -> statement_list statement 
Rule 9  statement_list -> statement 
Rule 10 control_statement -> loop 
Rule 11 control_statement -> if_statement 
Rule 12 compound_statement -> CURLY_OPEN statement_list CURLY_CLOSE 
Rule 13 compound_statement -> CURLY_OPEN CURLY_CLOSE 
Rule 14 definition -> fn_def 
Rule 15 definition -> var_def 
Rule 16 fn_def -> DEFN ID ARROW type invariants statement 
Rule 17 var_def -> type assignment 
Rule 18 assignment -> ID ASSIGN expression 
Rule 19 loop -> for_loop 
Rule 20 loop -> foreach_loop 
Rule 21 loop -> tilde_loop 
Rule 22 for_loop -> FOR statement statement statement compound_statement 
Rule 23 foreach_loop -> FOREACH ID IN expression compound_statement 
Rule 24 tilde_loop -> statement TILDE constant TILDE 
Rule 25 if_statement -> IF condition compound_statement 
Rule 26 if_statement -> IF condition compound_statement elseif_list 
Rule 27 if_statement -> IF condition compound_statement elseif_list else 
Rule 28 if_statement -> ternary 
Rule 29 elseif_list -> ELSEIF condition compound_statement 
Rule 30 elseif_list -> ELSEIF condition compound_statement elseif_list 
Rule 31 else -> ELSE compound_statement 
Rule 32 ternary -> condition QUESTION_MARK expression COLON expression 
Rule 33 invariants -> invariants invariant 
Rule 34 invariants -> invariant 
Rule 35 invariants -> NONE 
Rule 36 invariant -> type ID COLON invariant_tests 
Rule 37 invariant_tests -> invariant_tests COMMA test 
Rule 38 invariant_tests -> test 
Rule 39 test -> ID operator constant 
Rule 40 test -> STAR 
Rule 41 expression -> declarator 
Rule 42 expression -> assignment 
Rule 43 expression -> container 
Rule 44 expression -> test 
Rule 45 expression -> constant 
Rule 46 type -> INT_T 
Rule 47 type -> DBL_T 
Rule 48 type -> STR_T 
Rule 49 type -> list_type 
Rule 50 operator -> GT_OP 
Rule 51 operator -> LT_OP 
Rule 52 operator -> GTE_OP 
Rule 53 operator -> LTE_OP 
Rule 54 operator -> EQ_OP 
Rule 55 operator -> NEQ_OP 
Rule 56 constant -> INT 
Rule 57 constant -> DBL 
Rule 58 constant -> STR 
Rule 59 declarator -> ID L_PAREN fn_args R_PAREN 
Rule 60 declarator -> ID 
Rule 61 fn_args -> fn_args COMMA expression 
Rule 62 fn_args -> expression 
Rule 63 container -> list 
Rule 64 list -> L_BRACE container_items R_BRACE 
Rule 65 list_type -> L_BRACE type R_BRACE 
Rule 66 container_items -> container_items COMMA container_item 
Rule 67 container_items -> container_item 
Rule 68 container_item -> expression 
Rule 69 container_item -> empty 
Rule 70 bool -> TRUE 
Rule 71 bool -> FALSE 
Rule 72 condition -> bool 
Rule 73 comment -> single_comment 
Rule 74 single_comment -> COMMENT_LINE 
Rule 75 empty -> <empty> 

ответ

1

Похоже она нуждается в точку с запятой, и она имеет конец из -input. Трудно сказать больше, не видя грамматики.

Соответствующая часть вашей грамматики:

(2) statement -> definition SEMICOLON 
(14) definition -> fn_def 

Это единственные произведения, в которых fn_def и definition происходят на правой стороне.

Понятно, что definition может быть уменьшено до statement, когда токен с прицелом SEMICOLON. Так как fn_def может отображаться только в действующей программе в месте, где его можно немедленно свести к definition (единственное производство - это единичное производство), fn_def должен следовать за SEMICOLON. Таким образом, ваш парсер был правильным, и ваш образец ввода был неграмматическим.

fn_def имеет только один выпуск:

(16) fn_def -> DEFN ID ARROW type invariants statement 

, в которой становится очевидным, что последний элемент в fn_def является statement. Некоторые заявления (definition и expression) должны быть прерваны ;; если fn_defstatement является одним из таких (предположительно, это выражение, поскольку не похоже, что одно определение делает интересным тело функции), то fn_def нужно будет записать с двумя точками с запятой. Я сомневаюсь, что это то, что вы хотели.

definition заканчивается либо statement (если это fn_def) или с expression (если это var_def). Вы попытались определить statement так, чтобы он был саморазграничен (т.е. он заканчивается точкой с запятой, если он не заканчивается }, который завершает compound_statement. Таким образом, fn_def уже либо заканчивается точкой с запятой, либо закрывающей скобой, t требует другую точку с запятой. С другой стороны, var_def заканчивается выражением и, следовательно, делает это. Поэтому одним из решений было бы толкать конечную точку с запятой в var_def.

Редакционный комментарий, не связанный с конкретным вопросом спрашивает:

На самом деле, нет никакой очевидной причины, почему вам необходимо ограничить цикл или условные тела в составные операторы, кроме собственной эстетики; если вы разрешаете лямбда-телу быть не-составным заявлением, нет очевидной причины, по которой вы ограничиваете цикл for. Грамматику можно заставить работать в любом случае.

+0

Я редактировал в своей грамматике, но он довольно длинный и уродливый. Что заставляет вас думать, что ему нужна точка с запятой? – sdasdadas

+0

@sdasdadas: потому что состояние 113 говорит, что оно уменьшится, только если точка поиска точки с запятой – rici

+0

Благодарим вас за ваш ответ и комментарий в конце. Вы были невероятно полезны во всех моих вопросах о грамматике. Что касается вашего комментария, я видел несколько ошибок, возникающих у программистов, использующих одиночные утверждения в структурах управления, а затем добавляя другое утверждение, думая, что оно также будет находиться в структуре управления. Но у меня нет предусмотрительности или опыта, чтобы знать, будет ли это иметь последствия в моей грамматике. – sdasdadas