如果参数超过7个零,函数返回零 [英] Function returns zero if parameter has more than 7 zeros
问题描述
我用haskell函数编写了一个以pi为参数的精确数字:
mojePi :: Integer - >浮动
mojePi x = sqrt $ 6 * mySum x
其中
mySum 1 = 1
mySum x = sum $ map(1 /)$ map(** 2)[y ,y-1..1]
其中
y = fromInteger x
如果我用 10000000
(7个零)来运行这个函数,它可以正常工作,但是使用 100000000
(8个零)立即返回 0
。
为什么会发生这种情况?
原因如下:
>让y :: Float; y = fromInteger(100000000 :: Integer)
> y == y-1
True
> [y,y-1..1]
[]
基本上, Float
不能从10 ^ 8向下计数到1,单位步数。
<四舍五入错误令 y
和 y-1
相同的数字,因此符号 [y,y-1..1]
被解释为一个增加的序列,如eg [10,10 .. 1]
。由于起始值已经超过 1
,所以没有元素被放到输出列表中。
a href =https://www.haskell.org/onlinereport/haskell2010/haskellch6.html#x13-1310006.3.4 =nofollow noreferrer> Haskell 2010年报告:
序列
enumFromThenTo e1 e2 e3
是列表[e1,e1 + i, e1 + 2i,... e3]
,其中增量i
是e2 - e1
。如果增量为
正数或零,则当下一个元素大于e3
时,该列表将终止。如果e1>则列表为空。 E3
。如果增量为
为负,则当下一个元素小于
e3
;如果e1 < e3
。
可以说,Haskell对于递增和递减范围应该有不同的符号。对于 [y,y-1 .. 1]
,我想 repeat y
code> [] 。
I wrote in haskell function wich counts pi number with precision given as parameter:
mojePi :: Integer -> Float
mojePi x = sqrt $ 6 * mySum x
where
mySum 1 = 1
mySum x = sum $ map (1/) $ map (**2) [y,y-1..1]
where
y = fromInteger x
If I run this function with 10000000
(7 zeros) it works fine, but with 100000000
(8 zeros) and more it immediately returns 0
.
Why it happens?
Here's why:
> let y :: Float ; y = fromInteger (100000000 :: Integer)
> y == y-1
True
> [y, y-1 .. 1]
[]
Basically, a Float
can not count from 10^8 downwards to 1, with unit steps.
Rounding errors make y
and y-1
the same number, hence the notation [y,y-1 .. 1]
is interpreted as an increasing sequence, like e.g. [10,10 .. 1]
. Since the starting value is already over 1
, no element gets put in the output list.
Quoting from the Haskell 2010 report:
The sequence
enumFromThenTo e1 e2 e3
is the list[e1,e1 + i,e1 + 2i,…e3]
, where the increment,i
, ise2 − e1
. If the increment is positive or zero, the list terminates when the next element would be greater thane3
; the list is empty ife1 > e3
. If the increment is negative, the list terminates when the next element would be less thane3
; the list is empty ife1 < e3
.
Arguably, Haskell should have different notations for increasing and decreasing ranges. For [y, y-1 .. 1]
, I guess repeat y
would be a less surprising output than []
.
这篇关于如果参数超过7个零,函数返回零的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!