2011-03-21 87 views
4

我相信我很难理解轮班如何减少冲突的工作。我知道野牛可以向前看,所以我不明白我为什么会遇到这个问题。野牛:轮班减少冲突

在我的语言中,列表定义为[]之间的一组数字或列表。 例如[] [1] [1 2] [1 [2] 3]都是有效的列表。

下面是导致问题的

value: num 
    | stringValue 
    | list   
    ; 

list: LEFTBRACE RIGHTBRACE 
    | LEFTBRACE list RIGHTBRACE 
    | num list   
    | RIGHTBRACE    
    ; 

冲突从发生数的定义,它不知道天气由列表规则转移,或由价值规律减少。我很困惑,因为它不能检查一个列表是否跟在数字后面?

任何煽动我应该如何进行将不胜感激。

回答

6

我想我会定义不同的事情,以避免开始与问题的方式,是这样的:

value: num 
    | stringvalue 
    | list 
    ; 

items: 
    | items value 
    ; 

list: LEFTBRACE items RIGHTBRACE; 

编辑:分离号码清单从字符串列表无法做到干净除非你消除空列表。出现的问题是,您希望允许将空列表包含在数字列表中的字符串列表中,但查看空列表本身并不会让解析器决定哪个列表。例如:

[[] [] [] [] [] [] [] [] 1]

要弄清楚什么样的名单,这是,解析器将不得不看一直到1 - 但LALR(N)解析器只能预测N个符号来做出该决定。 Yacc(和Byacc,Bison等)只能执行LALR(1),所以他们只能向前看一个符号。这使得几种可能性:

  1. 消除空名单的可能性完全
  2. 有词法分析器将连续空列表任意数量的作为单个令牌
  3. 使用解析器生成器,不限于LALR(1)文法

里面一个yacc语法,但是,我不认为有什么可以做 - 你的语法根本放不下YACC的局限性。

+0

有时很高兴为空比赛发表评论,以便更容易看到。 'item:/ * Empty * /' – 2011-03-21 19:00:59

+0

@Martin:有时是真的 - 同时,任何能够读取yacc-like语法的人都会很容易地识别它。 – 2011-03-21 19:18:57

+0

这不会允许字符串在数字列表中吗?有没有办法确保列表中只有一种类型? – Pieces 2011-03-21 19:51:04

1

使用自下而上的解析器,通常是避免右递归的好主意,这是您在下面的语法的星号行中所具有的。

list: LEFTBRACE RIGHTBRACE 
    | LEFTBRACE list RIGHTBRACE 
    **| num list**   
    | RIGHTBRACE 

相反,你有没有想过这样的事情?

value:value num 
    | value string 
    | value list 
    | num 
    | string 
    | list 

list: LEFTBRACE RIGHTBRACE 
    | LEFTBRACE value RIGHTBRACE 

这样你就没有权利递归,而且语法的嵌套逻辑更简单地表达了。

+0

好吧,它是自顶向下的解析器,你想避免左递归? – Pieces 2011-03-21 19:48:10

+1

@Peces:对于您要使用右递归的自顶向下解析器。对于自下而上的解析器,左递归通常是首选。 – 2011-03-21 19:50:25