haskell - 如何将所有零移掉?

标签 haskell bit-manipulation ghc

这是 my last question 的后续内容。我成功地实现了一个相当快的“位队列生成器”

data BitQueueB = BQB !Word !Word

通过从左侧插入元素(从保护位开始),然后当我完成“构建”队列时,计算尾随零并将其移开,在左侧安装一个新的保护位。

但是,此解决方案对于 GHC < 7.10 并没有真正做任何事情,因为那是引入 countTrailingZeros 的时候。我也忍不住想知道是否有一些更神奇的方法来完成这种转变,或者是向左的对应。

要点

我有一个双字的两个字表示,保证至少设置了一位。我正在寻找最快的方法将双字移至左侧右侧,直到第一个设置位被移走,而不使用 countLeadingZeroscountTrailingZeros.

一个想法

我在这些问题上的糟糕直觉表明,如果我切换到左移,是否可以通过某种方式使用乘法,但也许这只是一厢情愿的想法。

最佳答案

左边更烦人。未实际测试:

m = x
m |= m >> 1
m |= m >> 2
m |= m >> 4
m |= m >> 8
m |= m >> 16
x = x * (0x80000000 / (m >> 1))

首先计算数字中存在的 2 的最高幂,然后乘以将其转换为 2 的最高可能幂所需的量,从而将最高设置位移动到顶部。它不喜欢最高位已经设置(它会除以 0)并且需要知道位数。因此,最好只计算前导零而不是这个,或者也许有更好的东西,但我不知道。

右边的版本(为了完整性?)更好,只是

x / (x & -x)

其中x & -x是一个相对众所周知的隔离最低设置位的技巧。

关于haskell - 如何将所有零移掉?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/37035643/

相关文章:

haskell - 无限计数器的无限列表

c++ - 在 Haskell 项目中包含 C++ 源代码

就类型安全而言,Haskell 类型与 newtype

go - 是否可以使用按位运算在随机 unicode 字符串中查找重复字符?

haskell - 在 Template Haskell AST 中重新关联树

haskell - GHC的非懒惰分支

haskell - Haskell 运行时如何区分指针和未装箱的字大小值?

haskell - 快速排序的比较次数

java - 为这些类型的字节级操作进行 Java 编码的最佳方法是什么?

JavaScript trunc() 函数