Haskell函数和let语句

时间:2014-07-07 03:24:21

标签: haskell

在GHCi中,我可以做到以下几点:

ghci> let ddd n = [0..n]
ghci> ddd 10
[0,1,2,3,4,5,6,7,8,9,10]

但是,如果我在文件中定义类似的函数:

ddd :: Int -> [a]
ddd n = [0..n]

在GHCi中加载文件后,出现以下错误

ghci> :l dsp.hs
[1 of 1] Compiling Main             ( dsp.hs, interpreted )

dsp.hs:43:13:
    Couldn't match expected type `a' with actual type `Int'
      `a' is a rigid type variable bound by
          the type signature for ddd :: Int -> [a] at dsp.hs:42:8
    In the expression: n
    In the expression: [0 .. n]
    In an equation for `ddd': ddd n = [0 .. n]
Failed, modules loaded: none.

任何原因??

由于

2 个答案:

答案 0 :(得分:6)

那是因为您要返回[a]而不是[Int]的列表,这应该有效:

ddd :: Int -> [Int]
ddd n = [0..n]

或者,如果您想要更通用的解决方案:

ddd :: (Num a, Enum a) => a -> [a]
ddd n = [0..n]

答案 1 :(得分:3)

如果我们启用ExplicitForAll扩展程序,我们可以看到您提供的类型签名与

相同
ddd :: forall a. Int -> [a]

如果没有写出forall,则会隐含ExplicitForAll,但a扩展名明确表示。{/ p>

但是,事实并非如此!对于所有类型Int,您的定义不起作用,仅针对一种特定类型:Int -> [Int]。所以正确的签名是{{1}}。