Динамический приоритет операторов и ассоциативность в ANTLR4?

Я работал над грамматикой antlr4 для нотации Z (версия ISO UTF), и спецификация требует фазы lex, а затем "двухфазного" анализа. сначала вы помещаете его в набор токенов NAME (или DECORWORD), а затем анализируете полученные токены по правилам operatorTemplate в грамматике синтаксического анализатора спецификации, заменяете соответствующие токены, а затем, наконец, анализируете новый измененный поток токенов, чтобы получить AST.

у меня выше работает, но я не могу понять, как динамически установить приоритет и ассоциативность правил синтаксического анализатора, поэтому деревья синтаксического анализа неверны.

синтаксис оператора выглядит следующим образом (числа имеют приоритет):

-generic 5 rightassoc (_ → _)
-function 65 rightassoc (_ ◁ _)

я не вижу API для установки ассоциативности на правило, поэтому я попытался с семантическими предикатами, что-то вроде:

expression:
: {ZSupport.isLeftAssociative()}? expression I expression
| <assoc=right> expression i expression
;

или же

expression:
: {ZSupport.isLeftAssociative()}? expression i expression
| <assoc=right> {ZSupport.isRightAssociative()}? expression I expression
;

но потом я получаю "Следующие наборы правил взаимно леворекурсивны [выражение]"

это можно сделать?

1 ответ

Я смог сделать это, переместив семантический предикат:

expression:
: expression {ZSupport.isLeftAssociative()}? I expression
| <assoc=right> expression I expression
;

У меня сложилось впечатление, что это не сработает, основываясь на этом обсуждении: /questions/27199783/semanticheskie-predikatyi-antlr4-zavisyaschie-ot-konteksta-ne-rabotayut/27199784#27199784

... но, похоже, он работает правильно во всех моих тестовых случаях...

Другие вопросы по тегам