使用多个模式匹配,即使使用无点,也不可能有不同数量的参数!
foo True b = b + 2
foo _ = id
不起作用。但
foo True = (+2)
foo _ = id
一样。有时我们只能在函数的一部分中使用无点,所以......
为什么呢? GHC太难了吗? :'(
答案 0 :(得分:20)
为什么呢? GHC太难了吗?
否即可。 GHC并不是太难。实际上,这是Haskell报告的错误。
请参阅:Haskell Report 2010 > Declarations and Bindings > Function bindings
函数绑定将变量绑定到函数值。变量x的函数绑定的一般形式是:
x p1 1 ... p1 k match1
...
x pn 1 ... pn k matchn[...等等......]
翻译:函数的一般绑定形式在语义上与等式等式(即简单模式绑定):
x = \ x 1 ... x k - >
的情况(x 1 ,...,x k )(p11,...,p1k)match1
...
(pn1,...,pnk)matchn
其中x i 是新标识符。
(强调我的)
虽然函数定义在语义上等效于到lambda&例如,Mihai建议,它们不一定按照这种方式编译。
问题是,Haskell报告定义函数声明,使得必须在等式的左侧具有相同数量的输入。事实上,k
在第1和第n个函数声明行中保持相同(并且暗示,中间的所有行)都清楚地表明了这一点。 此是限制的原因; 与GHC的实施细节无关。
TL;博士
不允许它的选择只是风格问题。 - 奥古斯特
答案 1 :(得分:4)
每个函数方程必须具有相同数量的参数。这就是你的第一个例子失败的原因。
要解决此问题,请使用
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
是错误的,因为分支有不同的类型。
当然,这是挥手,幕后发生的实际事情更加复杂