【问题标题】:How can I bit-convert between Int and Word quickly?如何快速在 Int 和 Word 之间进行位转换?
【发布时间】:2020-09-24 10:38:38
【问题描述】:

Haskell base documentation 表示“A Word 是无符号整数类型,大小与 Int 相同。”

如何获取Int 并将其位表示转换为Word,所以我得到一个Word 值,其位表示与原始Int 相同(即使它们表示的数值将不同)?

不能使用fromIntegral,因为那会改变位表示。

可以使用the Bits class 循环遍历这些位,但我怀疑这会很慢 - 而且我不需要进行任何类型的位操作。我想要某种可以编译为无操作(或接近它)的函数,因为没有进行任何转换。

动机

我想使用IntSet 作为一个快速整数集实现——然而,我真正想在其中存储的是Words。我觉得我可以通过在它们之间快速转换来创建一个由IntSet 支持的WordSet。问题是,我不想按值转换,因为我不想截断Word 值的上半部分:我只想保持位表示相同。

【问题讨论】:

  • unsafeCoerce 似乎确实可以解决问题,但我不确定它是否值得信任。
  • unsafeCoerce# 的文档表明它可以(因为支持在相同大小的未装箱类型之间进行转换)。不过,我确实更喜欢 int2Word#word2Int#,因为它们更明确 - 最好有编译器的声音支持。
  • 您确定fromIntegral 更改了位表示吗?比如我用ghci运行fromIntegral (2147483648 :: Word32) :: Int32,它返回-2147483648,这是正确的等价位表示。
  • 这是一个strange implementation,它确实进行了位转换——我承认没有尝试过,因为这种行为完全令人惊讶,完全不是我对fromIntegral的期望。
  • @IsaacvanBakel 事实上,fromIntegral :: Int -> Word 确实 保留位模式,fromIntegral :: Word -> Int 也是如此。由于fromIntegral = fromInteger . toIntegerInteger2^(WORD_SIZE_IN_BITS-1)< x < 2^WORD_SIZE_IN_BITS - 1 之间的整数表示错误,这看起来像是一个值转换,但这是值中的位模式保留。为了获得更好的性能,该实现有一个 GHC 重写规则,将 fromInteger 替换为 int2Word#word2Int#

标签: haskell integer word


【解决方案1】:

int2Word#/word2Int# in GHC.Prim 执行位转换。您可以使用它们轻松实现在盒装Int/Word 之间转换的包装器函数。

【讨论】:

    猜你喜欢
    • 2014-11-23
    • 1970-01-01
    • 1970-01-01
    • 2018-01-22
    • 1970-01-01
    • 2020-01-25
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多