Unsafe.Coerce.unsafeCoerce
может конвертировать между типами, как в C ++ reinterpret_cast<>
. Используйте с осторожностью.
В противном случае вы можете реализовать собственное декодирование IEEE-754 , используя RealFloat
.
bitsAsIEEE754 :: (Bits a, Integral a, RealFloat b) => a -> b
bitsAsIEEE754 word =
assert (floatRadix float == 2) $
assert (bitSize word == 1 + es + ms) $
assert (1 `shiftL` es == maxE - minE + 3) $
float
where
ms = floatDigits float - 1
(minE, maxE) = floatRange float
es = length $ takeWhile (< maxE - minE + 2) $ iterate (* 2) 1
sgn = if testBit word (ms + es) then negate else id
e = fromIntegral $ word `shiftR` ms .&. (1 `shiftL` es - 1)
nor = if e == 0 then id else flip setBit ms
m = sgn . toInteger . nor $ word .&. (1 `shiftL` ms - 1)
float = encodeFloat m $ max minE (e + minE - 1) - ms - 1
По крайней мере, с моим GHC кажется невозможным создать -0
и NaN
с использованием encodeFloat
, но все остальное должно работать.