我如何总结Double
?我以为sum
开箱即用,当我只是使用类型推断时,确实确实可以,但是当我给出将输出类型固定为Double
的类型签名时,总和就是无限的! / p>
这不起作用:
doubles :: Int -> Int -> Double
doubles maxk maxn = sum [1/(fromIntegral(i*(j+1)^(2*i)))|i<-[1..maxk],j<-[1..maxn]]
我看到这种行为:
*Main> doubles 20 1500
Infinity
但是,没有类型签名,相同的代码:
doubles maxk maxn = sum [1/(fromIntegral(i*(j+1)^(2*i)))|i<-[1..maxk],j<-[1..maxn]]
产生一个明智的答案:
*Main> doubles 20 1500
0.692481179869307
有什么作用?
答案 0 :(得分:5)
第二个函数的类型与第一个不同。
(分数a1,积分a2)=> a2-> a2-> a1
这里a2是具有Integral实例的任何类型。 Int和Integer都实现积分。整数是一个任意精度类型:无论大小如何,它都可以容纳任何数字,最高可达计算机内存的大小。诠释不是。例如:
(10 :: Integer)^ 100 == 10000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000
(10 :: Int)^ 100 == 0
第二种情况可能发生在您的第一个函数中。然后 1/0 == Infinity
当没有显式类型声明时,Haskell将假定任何自然数文字实际上是Integer。这就是第二个函数在Integers上运行且结果更好的原因