ANTLR 语法和语法谓词中的左值意识

发布于 2024-12-23 17:36:15 字数 1429 浏览 1 评论 0原文

我正在使用 ANTLR for D 实现一个解析器。这种语言基于 C,因此声明和表达式存在一些歧义。考虑一下:

a* b = c; // This is a declaration of the variable d with a pointer-to-a type.
c = a * b; // as an expression is a multiplication.

由于第二个示例只能出现在赋值表达式的右侧,因此我尝试使用以下代码片段来解决此问题:

expression
  : left = assignOrConditional
    (',' right = assignOrConditional)*
  ;

assignOrConditional
  : ( postfixExpression ('=' | '+=' | '-=' | '*=' | '/=' | '%=' | '&=' | '|=' | '^=' | '~=' | '<<=' | '>>=' | '>>>=' | '^^=') )=> assignExpression
  | conditionalExpression
  ;

assignExpression
  : left = postfixExpression
    ( op = ('=' | '+=' | '-=' | '*=' | '/=' | '%=' | '&=' | '|=' | '^=' | '~=' | '<<=' | '>>=' | '>>>=' | '^^=')
      right = assignOrExpression
    )?
  ;

conditionalExpression
  : left = logicalOrExpression
    ('?' e1 = conditionalExpression ':' e2 = conditionalExpression)?
  ;

据我的理解,这应该可以避免歧义,但测试失败了。如果我向解释器提供任何输入,从规则 allocateOrConditional 开始,它将失败并出现 NoViableAltException。 输入是

a = b
b-=c
d

也许我误解了谓词是如何工作的,因此如果有人可以纠正我对代码的解释,那就太好了:如果输入可以作为 postfixExpression 读取,它将检查 postfixExpression 之后的下一个标记是否是以下之一赋值运算符,如果是,它会将规则解析为赋值表达式。 (请注意,赋值表达式和条件表达式效果很好)。如果下一个标记不属于它们,它会尝试将其解析为条件表达式。

编辑 [已解决] 现在,我可以意识到这个解决方案还有另一个问题:如果它被链接起来,则赋值表达式必须在其右侧表达式中选择再次赋值(即,后缀和赋值运算符紧随其后)。

知道我的理解有什么问题吗?

I am implementing a parser with ANTLR for D. This language is based on C so there are some ambiguity around the declarations and the expressions. Consider this:

a* b = c; // This is a declaration of the variable d with a pointer-to-a type.
c = a * b; // as an expression is a multiplication.

As the second example could only appear on the right of an assignment expression I tried to resolve this problem with the following snippet:

expression
  : left = assignOrConditional
    (',' right = assignOrConditional)*
  ;

assignOrConditional
  : ( postfixExpression ('=' | '+=' | '-=' | '*=' | '/=' | '%=' | '&=' | '|=' | '^=' | '~=' | '<<=' | '>>=' | '>>>=' | '^^=') )=> assignExpression
  | conditionalExpression
  ;

assignExpression
  : left = postfixExpression
    ( op = ('=' | '+=' | '-=' | '*=' | '/=' | '%=' | '&=' | '|=' | '^=' | '~=' | '<<=' | '>>=' | '>>>=' | '^^=')
      right = assignOrExpression
    )?
  ;

conditionalExpression
  : left = logicalOrExpression
    ('?' e1 = conditionalExpression ':' e2 = conditionalExpression)?
  ;

As far as my understanding goes, this should do the trick to avoid the ambiguity but the tests are failing. If I feed the interpreter with any input, starting with the rule assignOrConditional, it will fail with NoViableAltException.
the inputs were

a = b
b-=c
d

Maybe I'm misunderstanding how the predicates are working therefore it would be great if someone could correct my explanation to the code: If the input can be read as a postfixExpression it will check if the next token after the postfixExpression is one of the assignment operators and if it is, it will parse the rule as an assignmentExpression. (Note, that the assignmentExpression and the conditionalExpression works well). If the next token isn't of them, it tries to parse it as a conditionalExpression.

EDIT
[solved] Now, there's an other problem with this solution that I could realize: the assignmentExpression has to choose in it's right hand expression is an assignment again (that is, postfix and assignment operator follows), if it is chained up.

Any idea what's wrong with my understanding?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

迟月 2024-12-30 17:36:15

如果我向解释器提供任何输入,...

不要使用 ANTLRWorks 的解释器:它有问题,并且忽略任何类型的谓词。使用它的调试器:它工作完美。

如果输入可以作为后缀表达式读取,它将检查后缀表达式之后的下一个标记是否是赋值运算符之一,如果是,它将将该规则解析为赋值表达式。

你是对的。

编辑[已解决]现在,我可以意识到这个解决方案还有另一个问题:如果它是链接的,则赋值表达式必须在其右侧表达式中选择再次赋值(即,后缀和赋值运算符跟随)向上。

这有什么问题吗?

If I feed the interpreter with any input, ...

Don't use ANTLRWorks' interpreter: it is buggy, and disregards any type of predicate. Use its debugger: it works flawlessly.

If the input can be read as a postfixExpression it will check if the next token after the postfixExpression is one of the assignment operators and if it is, it will parse the rule as an assignmentExpression.

You are correct.

EDIT [solved] Now, there's an other problem with this solution that I could realize: the assignmentExpression has to choose in it's right hand expression is an assignment again (that is, postfix and assignment operator follows), if it is chained up.

What's wrong with that?

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文