使用多个模式匹配,不同数量的参数是不可能的,即使是无点!
foo True b = b + 2
foo _ = id
例如不起作用。但
foo True = (+2)
foo _ = id
做。有时我们只能在函数的一部分中使用无点,所以...
为什么?GHC太难了吗?:'(
为什么?GHC太难了吗?
没有。GHC 一点也不难。实际上,这是 Haskell 报告的错误。
请参阅:Haskell 报告 2010 > 声明和绑定 > 函数绑定
函数绑定将变量绑定到函数值。变量 x 的函数绑定的一般形式是:
x p1 1 … p1 k match1
…<br> x pn 1 … pn k matchn[……呜呜呜……]
翻译:函数的一般绑定形式在语义上等价于等式(即简单模式绑定):
x = \ x 1 … x k -> case (x 1 , …, x k )
(p11, ..., p1k) match1
...<br> (pn1, ..., pnk) matchn
其中 x i是新的标识符。
(强调我的)
虽然函数定义在语义上等同于 lambda & case 表达式,但它们不一定像 Mihai 所建议的那样编译。
问题是,Haskell 报告定义了函数声明,使得它们在等式左侧必须具有相同数量的输入。k
这一点通过在第 1 和第 n 个函数声明行(并且暗示,在其间的所有行)上保持相同的事实清楚地表明。这就是限制的原因;它与 GHC 的实现细节无关。
tl;博士
选择不允许它只是风格问题。– 八月
每个函数方程必须具有相同数量的参数。这就是您的第一个示例失败的原因。
要修复它,请使用
foo True b = b + 2
foo _ x = id x
如您所见,两个方程具有相同数量的参数。
涉及模式匹配的多个方程被转换为案例表达式。在您的情况下foo
,大致翻译为
foo a b = case a of
True -> b + 2
_ -> id x
的两个(所有)分支case
必须具有相同的类型,因此您的第一个示例将被翻译为
foo a b = case a of
True -> b + 2
_ -> id
是错误的,因为分支有不同的类型。
当然,这是挥手,幕后发生的实际事情要复杂得多