hindent
将我的代码更改为:
do download i inputFile
onException
(callProcess (List.head args) (List.tail args))
(removeFileIfExists name)
`finally` removeFileIfExists inputFile
我无法确定finally
是否适用于do
块的其余部分,或仅适用于以onException
开头的状态。根据{{3}},
如果您在列表中看到意外的内容,例如在哪里,请插入一个 关闭括号,而不是分号。
我不确定该规则是否适用于此。
`finally`
是否适用于do的其余部分,或仅仅是最后一个声明以及为什么?
答案 0 :(得分:4)
我们可以找到使用GHCi:写作
Prelude> let f = (>>)
Prelude> :{
Prelude| do print 5
Prelude| print 4
Prelude| `f` print 3
Prelude| print 2
Prelude| :}
导致以下类型错误(不是解析错误!)
<interactive>:12:8: error:
• Couldn't match expected type ‘(() -> IO ()) -> Integer -> IO b’
with actual type ‘IO ()’
• The function ‘print’ is applied to three arguments,
but its type ‘Integer -> IO ()’ has only one
In the second argument of ‘f’, namely ‘print 3 print 2’
In the expression:
do { print 5;
print 4 }
`f` print 3 print 2
查看列表行,我们发现GHCi如何解析代码,该代码使用显式括号和分号打印。
在那里,我们看到`f`
部分已关闭 do
块!这使得整个do
块成为f
的第一个参数。此外,下一行不再在块中,现在形成单个表达式print 4 print 2
,用作f
的第二个参数。这会触发类型错误,因为它使用三个参数调用print
。
实际上,大括号}
是在`f`
之前插入的,因为OP提到的规则:当某个块没有解析时,我们添加}
并继续。
总结一下,如果`f`
缩进更多,则该块被解析为
do print 5
print 4 `f` print 3
print 2
如果`f`
缩进为上一行,或 less ,则该块将被解析为
(do { print 5
; print 4 }) `f` print 3 print 2
我建议尽量避免缩进`f`
与前一行完全一致:最好缩进它,这样即使对于人类读者来说,解析也很明显。