繁体   English   中英

解析快乐:左递归与右递归

[英]Parsing with Happy: left-recursion versus right-recursion

Happy用户手册的2.2节建议你使用左递归而不是右递归,因为右递归是“低效的”。 基本上他们说如果你试图解析一长串项目,右递归将溢出解析堆栈,而左递归使用常量堆栈。 给出的典型例子是

items : item            { $1 : [] }
      | items "," item  { $3 : $1 }

不幸的是,这意味着项目列表向后出现。

现在很容易在最后应用reverse (尽管令人讨厌的是你必须在调用解析器的每个地方执行此操作,而不是在定义它的地方执行此操作)。 但是,如果项目列表很大,肯定reverse 也会溢出Haskell堆栈? 没有?

基本上,我如何制作它,以便我可以解析任意大的文件,仍然以正确的顺序得到结果?

如果您想要的是每次都要reverse的所有items ,您可以定义

items  : items_           {reverse $1}

items_ : item             { $1 : [] }
       | items_ "," item  { $3 : $1 }

reverse不会溢出堆栈。 如果您需要说服自己,请尝试评估length $ reverse [1..10000000]

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM