Fut*_*iti 9 haskell monomorphism-restriction
为什么允许这样做:
i :: Num a => a
i = 1
Run Code Online (Sandbox Code Playgroud)
虽然这些都是不允许的:
i' :: Num a => a
Just i' = Just 1
x, y :: Num a => a
(x, y) = (1, 2)
x :: Num a => a
y :: Num a => a
(x, y) = (1, 2)
y :: Num a => a
x :: Num a => a
(x, y) = (1, 2)
m :: ()
n :: Num a => a
(n, m) = (1, ())
n :: Num a => a
m :: ()
(n, m) = (1, ())
Run Code Online (Sandbox Code Playgroud)
除非通过 关闭单态限制{-# LANGUAGE NoMonomorphismRestriction #-},否则尝试使用其中任何一个进行编译总是会导致“重载签名与单态限制冲突”。
但我不是已经在这里指定了所有类型吗?单态限制首先是怎么出现的呢?
引用规则:
我们说给定的声明组是不受限制的当且仅当:
(a):组中的每个变量都由函数绑定或简单模式绑定(第 4.4.3.2 节)绑定,并且
(b):显式类型签名为组中通过简单模式绑定绑定的每个变量给出。
什么是简单的模式绑定?有两个相互矛盾的定义。
(4.5.5 单态性限制)简单模式绑定是其中模式仅由单个变量组成的模式绑定
和
(4.4.3.2 模式绑定) 简单的模式绑定具有形式
p = e
根据第一个定义,失败的绑定都不是简单的,因此它们不能不受限制,这意味着单态限制适用于它们。根据第二个定义,一切都是简单且不受限制的,即不应该应用单态性限制。
适用的定义应该是本文中详细介绍的第一个定义,这就是编译器正在使用的定义,但 AFAICT 报告未更新以反映这一点。