为什么这个类型检查:
runST $ return $ True
Run Code Online (Sandbox Code Playgroud)
虽然以下不是:
runST . return $ True
Run Code Online (Sandbox Code Playgroud)
GHCI抱怨:
Couldn't match expected type `forall s. ST s c0'
with actual type `m0 a0'
Expected type: a0 -> forall s. ST s c0
Actual type: a0 -> m0 a0
In the second argument of `(.)', namely `return'
In the expression: runST . return
Run Code Online (Sandbox Code Playgroud) 鉴于以下定义:
import Control.Monad.ST
import Data.STRef
fourty_two = do
x <- newSTRef (42::Int)
readSTRef x
Run Code Online (Sandbox Code Playgroud)
以下在GHC下编译:
main = (print . runST) fourty_two -- (1)
Run Code Online (Sandbox Code Playgroud)
但这不是:
main = (print . runST) $ fourty_two -- (2)
Run Code Online (Sandbox Code Playgroud)
但随后bdonlan在评论中指出,这确实编译:
main = ((print . runST) $) fourty_two -- (3)
Run Code Online (Sandbox Code Playgroud)
但是,这不编译
main = (($) (print . runST)) fourty_two -- (4)
Run Code Online (Sandbox Code Playgroud)
这似乎表明(3)只是由于中缀的特殊处理而编译$,但是,它仍然没有解释为什么(1)编译.
问题:
1)我已经阅读了以下两个问题(第一,第二),并且我被引导相信$只能用单态类型实例化.但我同样假设.只能用单态类型进行实例化,结果同样会失败.为什么第一个代码成功但第二个代码没有?(例如,GHC对第一种情况有特殊规则,它不能在第二种情况下适用吗?)
2)是否有当前的GHC扩展编译第二个代码?(也许ImpredicativePolymorphism在某些时候这样做了,但它似乎已被弃用,有什么东西取而代之吗?)
3)有没有办法定义说`my_dollar`使用GHC扩展做什么$,但也能够处理多态类型,所以(print . runST) `my_dollar` …