使用浮点运算对整数数据进行右旋运算?

时间:2011-05-09 04:58:10

标签: floating-point integer bitwise-operators

我想用无符号整数表示取一个值,不知何故,使用浮点运算,执行一个向右旋转的按位运算。

看看这里使用的聪明才智:http://en.wikipedia.org/wiki/Fast_inverse_square_root 这使用魔术值和一些技巧来使用整数运算对浮点数执行操作。我想要的是相反的;我使用的硬件针对浮点进行了大量优化,但在整数运算方面表现不佳。该算法是sha256,它大量使用了右旋操作。

1 个答案:

答案 0 :(得分:2)

我想到了两种方法:

  • 获取包含整数的位,将它们填充到一个变量中,该变量期望保持具有相同位数的浮点数,并对这些位进行操作,就好像它们是浮点数一样。希望硬件有一些浮点运算操作,这些操作与SHA256使用的整数运算相同。
  • 将整数填充到具有更多位的浮点变量(例如,将Int32放入Double,可以保存53位而不会丢失精度),然后使用数学运算实现旋转右运算。

第一种选择不太可行。如果您的硬件基于IEEE 754浮点标准(浮点表示的最常见标准),那么浮点数将存储为位域;例如,double有一个符号位,11个指数位和53个小数位。不会有任何操作将符号位的值移到指数位插槽之一。然后有一些具有特殊含义的位模式,并在整个操作中传递这种意义,如NaN和无穷大。所以整个想法可能都不是首发。

我不相信第二种方法也可行;你需要完全控制诸如舍入行为之类的东西,并且想要让自己相信你的浮点值中有正确的位数,你绝对需要大量的测试来说服自己它已经得到了一系列投入的预期产出。但是这里有。

旋转右操作 - 比方说,x ror y - 因此崩溃。设b是x中的位数。我假设一切都是使用无符号算术完成的,因为它使逻辑更加简单。

  • 我们从x ror y开始。
  • 可以表示为右移,左移和OR,(x shr y) or (x shl (b - y))
  • Shr与除以2的幂相同。 Shr会丢弃从低端掉落的任何位,因此我们可以通过使用floor函数来模拟它。现在我们有floor(x / 2^y) or (x shl (b - y))
  • Shl与乘以2的幂相同。 Shl会丢弃从上端掉落的任何位,我们可以通过乘法模2 ^ b来模拟。这给了我们floor(x / 2^y) or ((x * 2^(b - y)) mod 2^b)
  • 由于shl和shr的结果是不相交的(它们影响结果中的不同位),所以或者也可以通过加法完成。所以现在我们有整个旋转操作的数学符号:floor(x / 2^y) + ((x * 2^(b - y)) mod 2^b)

现在只需在每个地方插入该公式SHA256进行旋转右操作,看看它是否比整数运算更快。似乎不太可能但不是不可能 - 添加两个具有不同指数的浮点数将需要FP硬件内的快速移位操作,即使整数硬件没有快速移位。