以下代码无法编译:

import Data.Bits
xor2 = xor


但是,一旦我添加了类型信息,它就会编译:

import Data.Bits
xor2 :: Bits a => a->a->a
xor2 = xor


我无法解释这一点。有什么解释吗?

最佳答案

这是默认情况下启用的dreaded monomorphism restriction(MMR)的问题。 MMR是一个规则,除非看起来像函数(即x = ...x a = ...)的顶级绑定具有明确的多态类型签名,否则它们将强制具有单态绑定。

问题是Bits a => a -> a -> a是多态的(请注意类型变量a),Haskell不知道如何为a选择满足Bits约束的默认类型。

添加类型签名后,即可使用MMR,并且可以具有多态的顶级绑定。另一种选择是通过添加命名参数来“扩展”定义。由于xor2现在在语法上看起来像一个函数,因此MMR不适用:

xor2 x = xor x


您也可以使用语言扩展名关闭MMR。您可以将其放在模块顶部:

{-# LANGUAGE NoMonomorphismRestriction #-}

08-25 04:09