EBNF喜欢这个
Goal = Stmt
Stmt = "if" "expr" "then" Stmt ("else" Stmt)?
Stmt = "S"
我应该将其转换为
Goal = Stmt
X = "else" Stmt
Stmt = "if" "expr" "then" Stmt | "if" "expr" "then" Stmt X
Stmt = "S"
或者
Goal = Stmt
Stmt = "if" "expr" "then" Stmt | "if" "expr" "then" Stmt "else" Stmt
Stmt = "S"
这两个BNF对GLR解析器的意义是否相同?
------------------------ APPEND CONTENT --------------------- ---------
如果词法是
"if" "expr" "then" "if" "expr" "then" "S" "else" "S"
GLR解析器应该有两棵树
Goal
Stmt
"if"
"expr"
"then"
Stmt
"if"
"expr"
"then"
Stmt
"S"
"else"
Stmt
"S"
和
Goal
Stmt
"if"
"expr"
"then"
Stmt
"if"
"expr"
"then"
Stmt
"S"
"else"
Stmt
"S"
但是第一个转换后的BNF只能得到第一个树,因为当它遇到"else"
时,减少/转移没有冲突,冲突就是在满足X.
第二个BNF在遇到"else"
时会有一个减少/移位冲突,因此解析器将拆分为两个线程以在不同条件下解析。
我是对的吗?是否有任何ACTION,GOTO TABLE生成器会像第二个BNF一样处理第一个BNF?
答案 0 :(得分:1)
它们是等效的语法,将解析相同的语言。
您的X语法仅在一个地方使用X.净效果就好像X的主体被替换为X被引用。在实践中,拥有X生产将迫使解析器做更多的工作。除非你想为X的减少附加一个语义动作,否则这个额外的工作不会在效率上购买任何东西。
如果使用这种一次性使用会使语法更易于维护,那么这很有用。在这样的小语法中,我没有看到这一点。在实际的语法中(我们有IBM COBOL的GLR语法,有5000个产品[责怪IBM,而不是我们]),这样的结构可能非常有用,额外的解析开销并不重要。