我尝试使用解析器组合器在scala中编写解析器。如果我递归匹配,从用Scala编写的解析器返回有意义的错误消息
def body: Parser[Body] =
("begin" ~> statementList ) ^^ {
case s => { new Body(s); }
}
def statementList : Parser[List[Statement]] =
("end" ^^ { _ => List() })|
(statement ~ statementList ^^ { case statement ~ statementList => statement :: statementList })
然后我得到很好的errormessages,只要有语句错误。 但是,这是难看的长码。所以我想写这个:
def body: Parser[Body] =
("begin" ~> statementList <~ "end" ) ^^ {
case s => { new Body(s); }
}
def statementList : Parser[List[Statement]] =
rep(statement)
此代码的工作原理,但只打印有意义的消息,如果在FIRST语句中有错误。如果是在后面的声明中,该消息成为痛苦无法使用,因为解析器希望看到更换整个错误陈述的“结束”标记:
Exception in thread "main" java.lang.RuntimeException: [4.2] error: "end" expected but "let" found
let b : string = x(3,b,"WHAT???",!ERRORHERE!,7)
^
我的问题:有没有办法让代表和重新编辑与有意义的错误消息一起工作,将插入符号放在正确的位置而不是重复片段的开头?
'phrase'返回一个'Parser',只有当它接受了某些东西后没有输入时才会成功。不过,我不知道为什么这会改变这种回溯方式。 – 2010-12-11 23:43:36
事实证明,它根本不会改变回溯,但短语具有一点状态来检查具有最长匹配结果的故障。在Odersky书中关于解析器的章节中有一段称为“错误报告”。 – Jan 2010-12-15 11:56:08