这个反转位顺序功能怎么了?

时间:2010-04-24 19:50:26

标签: c bit-manipulation

我很惭愧地承认我不太了解比特和比特操作,因为我可能应该这样做。我本周末尝试通过写一些“反转位数”和“计数ON位”功能来解决这个问题。我从here中得到了一个例子,但是当我按照下面的方式实现它时,我发现我必须在< 29.如果我在< 32(如例子中所示)然后当我尝试打印整数(使用我写的printBits函数)时,我似乎错过了前3位。这对我没有意义,有人可以帮助我吗?

感谢大家的帮助,我添加了评论以显示我所做的更改。

int reverse(int n)
{
    int r = 0;
    int i = 0;
    for(i = 0; i < 29; i++) //Should be i < 32
    {
        r = (r << 1) + (n & 1); //| instead of + to make it obvious I'm handling bits
        n >>=1;
    }

    return r;
}

这是我的printBits函数:

void printBits(int n)
{
    int mask = 0X10000000; //unsigned int mask = 0X80000000;
    while (mask)
    {
        if (mask & n)
        {
            printf("1");
        }
        else
        {
            printf("0");
        }
        mask >>= 1;
    }
    printf("\n");
}

一个工作?反转功能

int reverse2(int n)
{
    int r = n;
    int s = sizeof(n) * 7; // int s = (sizeof(n) * 8) -1

    for (n >>= 1; n; n >>=1)
    {
        r <<=1;
        r |= n & 1;
        s--;


    r <<= s;
    return r;
}

5 个答案:

答案 0 :(得分:5)

int mask = 0X10000000;

在第28位放1。你想要0X80000000

答案 1 :(得分:3)

打印位错误,其0x80000000不是0x10000000。

>>> bin (0x80000000)  
'0b10000000000000000000000000000000'  
>>> bin (0x10000000)  
'0b10000000000000000000000000000'

见0x1 ......没有设置最高位。

答案 2 :(得分:3)

你有:

int mask = 0x10000000;

这里有两个问题。你没有设置高位,如果你这样做,它仍然(可能)不起作用,因为你的编译器会在签名的int上使用算术移位。

您想要将面具更改为:

unsigned int mask = 0x80000000;

对于算术移位,右移0x80000000将永远不会变为零,因为符号位将神奇地扩展到其他位。有关算术转换的详细信息,请参阅here

答案 3 :(得分:2)

而不是+,您应该使用|(按位或)。你应该使用< 32

答案 4 :(得分:1)

如上所述,这会将n的低29位反转为r。 n的前三位将保留在n中(向下移位29位)并且不返回。

如果你看到别的东西,我会怀疑你的printBits函数有问题。

修改

你的printBits函数打印n的低29位,所以这一切都有意义。