Java 中的反转位 - O(n)

reverse bits in Java - O(n)

我试图理解这段在 O(n) 时间内反转位的代码。我了解时间复杂度,但无法理解这段代码背后的逻辑。

public static long reverse(long a) {
    long result = 0;
    int i = 31;
    while(a > 0){

        result += (a % 2) * Math.pow(2, i);
        i--;                        
        a = a/2;
    }
    return result;
}

为简单起见,例如,如果我取 12(1100)且仅取 4 位(设置 i = 3),我的输出将是 3(0011)。我明白了,我也能得出答案。

但是有人可以解释这段代码背后的逻辑吗?谢谢!

那个密码是

  1. 中断了一半可能的位模式(所有负数),并且
  2. O(n),而不是 O(log n),其中 n 是 a
  3. 中的位数
  4. 效率很低
  5. 写得乱七八糟

该算法仅适用于正数并且:

extract the rightmost bit from a
set the corresponding bit from the left end
shift a one position to the right

它重复 a > 0。如果 a 的值有一些前导零位,那么这个算法会比 O(n) 好一点。

尽管现代编译器 应该 能够将 a/2 转换为 a >> 1a%2a & 0x00000001。但是我不知道它是否会将 Math.pow(2, i) 识别为 0x00000001 << i;

这是解释

i = 31 //number of bits in integer

以下分为两部分

result += (a % 2) * Math.pow(2, i);

(a % 2) 计算最后一位。 乘以 2 的正幂具有左移位的效果。 (Math.pow(2, i) 向左移动 i 次。

所以我们计算的是单位位置位,把它放在从单位位置开始的第i个位置,也就是从右边算起(31 - i),这有效地把位的位置从左到右反转了。

最后

i--; //move to next bit
a = a/2; //chop the unit place bit to proceed to next.

就是这样。