Bison 将右递归转换为左递归的通用方法

Bison 将右递归转换为左递归的通用方法,bison,yacc,Bison,Yacc,我最近与Flex和Bison合作。我知道,由于堆栈的大小,后一种方法通常不能很好地用于正确的递归。另一方面,大多数语法问题很容易用正确的递归来解决。有一种通用的算法可以将左递归转换为右递归。有相反的方法吗 下面是一个简单的例子: expression: number | expression operation number | expression operation openRound expression closeRound | openRound expressio

我最近与Flex和Bison合作。我知道,由于堆栈的大小,后一种方法通常不能很好地用于正确的递归。另一方面,大多数语法问题很容易用正确的递归来解决。有一种通用的算法可以将左递归转换为右递归。有相反的方法吗

下面是一个简单的例子:

expression:
    number
  | expression operation number
  | expression operation openRound expression closeRound
  | openRound expression closeRound

您可以将数字和运算视为终端,因为在本例中它们是不相关的。

有一些算法可以从语法中删除左递归或右递归(但不能同时删除两者)。这两种算法是彼此的简单镜像,因此您可以从移除左递归的算法中派生移除右递归的算法

然而,这些算法并不保留解析树。如果您只是试图识别某个字符串是否在该语言中,这并不重要,但当您真正想要解析该字符串时,这并不是很有用,因为解析意味着“分析字符串的语法结构”。在这种情况下,生成不正确的解析树毫无帮助

此外,这些算法不一定保留LR(1)语言集合中的成员身份,因此也有可能使用LR(1)解析算法不再能够解析(甚至无法识别)生成的语法

在任何情况下,我都反对“大多数……语法问题很容易用正确的递归解决”的说法。事实上,大多数实际的解析问题更容易用左递归解决,包括问题末尾的示例语法(左递归)。将这样的语法重新排列为右递归语法,以便LL解析器能够处理它,这是一个非常烦人的过程,其最终结果不如原始的左递归语法可读。

您的示例语法是左递归的,所以我不理解您的问题。