简体   繁体   English

为什么将int a = 1左移31位然后右移31位,它变为-1

[英]why shift int a=1 to left 31 bits then to right 31 bits, it becomes -1

given 给定

int a = 1; ( 00000000000000000000000000000001 ), 00000000000000000000000000000001 ),

what I did is just 我所做的只是

a=(a<<31)>>31;

I assume a should still be 1 after this statement (nothing changed I think). 我假设在此语句之后a仍应为1 (我认为没有改变)。 However, it turns out to be -1 ( 11111111111111111111111111111111 ). 但是,结果为-111111111111111111111111111111111 )。 Anyone knows why? 有人知道为什么吗?

What you are missing is that in C++ right shift >> is implementation defined. 您缺少的是在C ++中右移>>是实现的定义。 It could either be logical or arithmetic shift for a signed value. 对于有符号值,它可以是逻辑移位或算术移位。 In this case it's shifting in 1 s from the left to retain the sign of the shifted value. 在这种情况下,它会从左侧移1 s,以保留移位值的符号。 Typically you want to avoid doing shifts on signed values unless you know precisely that they will be positive or that the shift implementation doesn't matter. 通常,您希望避免对有符号值进行移位,除非您确切地知道它们将为正数或移位实现无关紧要。

Look at it in steps: 分步查看:

#include <cstdio>
using namespace std;

int main()
{
    int a = 1;
    printf("%d = %x\n", a, a);
    a <<= 31;
    printf("%d = %x\n", a, a);
    a >>= 31;
    printf("%d = %x\n", a, a);
    return 0;
}

Output: 输出:

1 = 1
-2147483648 = 80000000
-1 = ffffffff

1 got shifted all the way up to the high bit which makes it a negative number. 1一直移到最高位,这使其变为负数。 Shifting back down triggers sign extension to maintain the negative. 向后移会触发符号扩展,以保持负数。

Change the declaration of a to unsigned int a and you will get the behaviour you expect. 将a的声明更改为unsigned int a ,您将获得预期的行为。

" however it turns out to be -1 " “但是结果是-1

You use an unsigned int to do so for seeing only 32 bit values that are greater than 0 : 您使用unsigned int来查看仅大于0 32位值:

 unsigned int a = 1; 
 a=(a<<31)>>31;  

It is a signed shift so the left most bit will be extended. 这是一个有符号的移位,因此最左边的位将被扩展。 That way the overall number is on the same side of 0. 这样,总数就位于0的同一侧。

By left shifting that much you put the lowest bit into the sign bit and end up with a negative number. 左移那么多,您会将最低位放入符号位,最后得到负数。

When you then do a right shift it sign extends, copying the sign bit down to the lower 31 bits. 然后,当您右移时,符号会扩展,将符号位复制到低31位。

If you want to know the lowest bit just do & 1 . 如果您想知道最低位,请执行& 1

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM