在Java中获取反转的Integer

时间:2011-03-27 18:46:03

标签: java binary

Java中有一种方法可以反转Integer reverseBytes()中的位。我想尝试另一种实现,这就是我所拥有的:

public static int reverse(int num) {

        int num_rev = 0;
        for (int i = 0; i < Integer.SIZE; i++) {
            System.out.print((num >> i) & 1);

            if (((num >> i) & 1)!=0) {

                num_rev = num_rev | (int)Math.pow(2, Integer.SIZE-i);
            }

        }
        return num_rev;
}

结果num_rev不正确。有没有人知道如何“重建”价值?也许有更好的方法来执行它?

感谢您的任何建议。

3 个答案:

答案 0 :(得分:3)

反向位的正常方法是通过位操作,当然通过浮点数学例程!

例如(nb:未经测试)。

int reverse(int x) {
    int y = 0;
    for (int i = 0; i < 32; ++i) {
        y <<= 1;       // make space
        y |= (x & 1);  // copy LSB of X into Y
        x >>>= 1;      // shift X right
    }
    return y;
}

由于x右移并且y左移,结果是x的原始LSB最终成为y的MSB。

这是一个很好的(也是众所周知的)方法:

unsigned int reverse(unsigned int x)
{
    x = (((x & 0xaaaaaaaa) >> 1) | ((x & 0x55555555) << 1));
    x = (((x & 0xcccccccc) >> 2) | ((x & 0x33333333) << 2));
    x = (((x & 0xf0f0f0f0) >> 4) | ((x & 0x0f0f0f0f) << 4));
    x = (((x & 0xff00ff00) >> 8) | ((x & 0x00ff00ff) << 8));
    return ((x >> 16) | (x << 16));
}

这实际上是C代码,但由于Java没有unsigned类型移植到Java所有你应该做的就是删除unsigned限定符并使用>>>代替>>以确保您没有获得任何“签名延期”。

它首先交换每个其他,然后每隔一个位,然后每隔一个 nybble ,然后每隔一个 > byte ,然后是最后的16位和16位的单词。这实际上有效:)

答案 1 :(得分:0)

您的代码有两个问题:

  1. 你正在使用int cast。你应该做(长)Math.pow(... int cast的问题是pow(2,n)将永远是一个正数,所以pow(2,31)转换为int将被舍入到( 2 ^ 31)-1,因为那是最大的正int。2 ^ 31-1的位字段是0x7ffffff,但在这种情况下你需要0x80000000,这正是铸造long的低32位。< / LI>
  2. 你在做pow(2,Integer.Size - i)。那应该是Integer.SIZE - i - 1.你基本上想把第0位到最后一位,第1位到第二位,依此类推。但是,最后一位是第31位,而不是第32位。您的代码现在正尝试将位0设置为位Integer.SIZE-0 == 32,因此您需要减去1。
  3. 以上假设这只是为了好玩。但是,如果您确实需要反转位,不要使用浮点运算。做一些其他答案的建议。

答案 2 :(得分:-1)

为什么你不想使用:

public static int reverseBytes(int i) {
    return ((i >>> 24)           ) |
           ((i >>   8) &   0xFF00) |
           ((i <<   8) & 0xFF0000) |
           ((i << 24));
}

编辑: 整数也有:

public static int reverse(int i)
  

返回获取的值   颠倒了比特的顺序   二进制补码二进制表示   指定的int值。