我正在开发一个大型的Haskell程序,所以我只是包含了与此相关的代码,以使问题更加清晰。请评论我是否应该包含更多内容。
当我编译时,我只收到一条错误消息:"解析错误(可能是错误的缩进或括号不匹配)"
以下是一些没有错误的代码(printStmt)和一个非常相似的部分(VarDeclStmt),错误指向行读数," expr>> = \ s - >"。我不明白为什么一个人会好,另一个会引起问题。他们以什么方式不同?
Statement
答案 0 :(得分:4)
这是一个缩进问题。块
varDeclStmt = do
keyword "var" >>
expr >>= \s -> --ERROR
symbol "=" >>
expr >>= \e ->
return (VarDecl s e)
解析为
varDeclStmt = do
{ keyword "var" >>
; expr >>= \s -> --ERROR
; symbol "=" >>
; expr >>= \e ->
; return (VarDecl s e)
}
这是无稽之谈,因为第一个条目keyword "var" >>
无效。
请注意,进一步(或更少)缩进整个块不会改变它的解析方式。
最简单的解决方法是完全删除do
,以便下面的文本不会被解析为块,因此它不会被拆分成单独的条目,而是被解析为好像它在一行上。< / p>
否则,您可以切换到正确的do
表示法
varDeclStmt = do
keyword "var"
s <- expr
symbol "="
e <- expr
return (VarDecl s e)
或(最差的解决方案),使do
块成为单条目块,使块缩进多于第一行,如follos
varDeclStmt = do
keyword "var" >>
expr >>= \s ->
symbol "=" >>
expr >>= \e ->
return (VarDecl s e)
上述解决方案很愚蠢,因为do
的目的是将块拆分为条目,并且缩进是为了只有一个条目。所以,我们使用两件事来相互抵消。
答案 1 :(得分:2)
缩进错误与do
块有关。尝试在do
后缩进。类似的东西:
varDeclStmt = do
keyword "var" >>
expr >>= \s ->
symbol "=" >>
expr >>= \e ->
return (VarDecl s e)
如果有效,请告诉我。