float2Int似乎介于溢出2^^62,并2^^63为64位机器(我用GHC 7.6.1试图在英特尔的iMac).试图检查时,我才注意到这个问题maxBound了Int.在GHC中float2Int作为一个原始实现float2Int#.
GHCI提示输出低于- maxBound::Int是2^^63我的Intel Mac上.我也试过铸造2^^63到Float,然后还原值一点,看是否溢出消失(以考虑小舍入误差如果有的话).它没有:
?: maxBound :: Int
9223372036854775807
?: GHC.Float.float2Int $ 2^^63 -- overflows
-9223372036854775808
?: GHC.Float.float2Int $ (9223372036854775807::Float) -- now try actual value of 2^^63
-9223372036854775808
?: GHC.Float.float2Int $ (9223372036854000000::Float) -- reduce it a bit
-9223372036854775808
?: minBound :: Int -- overflow value is same as minBound::Int
-9223372036854775808
?: GHC.Float.float2Int $ 2^^62 + 2^^61 -- works fine here
6917529027641081856
Run Code Online (Sandbox Code Playgroud)
64位Int边界上的溢出是否是预期的行为?它似乎做工精细,直到2^^62和介于溢出2^^62和2^^63.我查了GHC trac,看看是否有任何报告错误,并没有发现任何错误.关于这个,我没有在SO上发现任何帖子.
这都是正确的行为.首先,让我们澄清一个小细节:
maxBound :: Int在我的intel mac上是2 ^^ 63
不,它应该是(2^63) - 1.减去一个是非常重要的,所以float2Int (2^^63)应该溢出.
那你的削减怎么样?考虑一下:
Prelude GHC.Float.RealFracMethods> let a = 9223372036854775807::Float
Prelude GHC.Float.RealFracMethods> let b = 9223372036854000000::Float
Prelude GHC.Float.RealFracMethods> a == b
True
Run Code Online (Sandbox Code Playgroud)
浮点数是近似值,并且您的减少不会导致浮点数发生重大变化.到目前为止的输入都等于2^63.
最后,
> 2^^62 + 2^^61 < (2^^63 :: Float)
True
Run Code Online (Sandbox Code Playgroud)
在上次测试时,您发现了一个数字,当被转换为Float时,表示为小于2^63,因此在64位范围内Int并产生您的预期值.
| 归档时间: |
|
| 查看次数: |
102 次 |
| 最近记录: |