C++中的 >> 是什么意思?

3
在这种情况下,>> 有什么作用?
int n = 500;
unsigned int max = n>>4;
cout << max;

它打印出31

它对500做了什么才能得到31

8个回答

9

位移操作!

500的原始二进制:
111110100

向左移动4位
000011111,即为31!

Original: 111110100
1st Shift:011111010
2nd Shift:001111101
3rd Shift:000111110
4th Shift:000011111 which equals 31.

这相当于通过16进行整数除法。

500/16 = 31
500/2^4 = 31

以下是一些从这里获取的事实:http://www.cs.umd.edu/class/spring2003/cmsc311/Notes/BitOp/bitshift.html(因为从我的头脑中涌出的话语会导致无效的胡言乱语,这些人表述得比我清楚)

使用 << 进行左移会导致从最低有效端(右侧)移动0,并导致从最高有效端(左侧)掉落位。

使用 >> 进行右移会导致从最高有效端(左侧)移动0,并导致位从最低有效端(右侧)掉落,如果数字是无符号的。

位移不会改变被移位的变量的值。 相反,将创建一个具有位移结果的临时值。


关于 ">>" 的部分有点模糊。"如果数字是无符号的" 部分适用于整个句子,而不仅仅是 "从右侧掉出的位"。此外,在C中,500 是有符号的! 500U 是无符号的。 - MSalters
好在这是C++。但无论如何,原始int是有符号的。如果数字是有符号的,则它取决于实现。它可以将位移过去同时保留符号位,或者它可以无论如何进行位移并翻转您的符号位(可能),或召唤DESTROYER GRAKNOR。老实说,这取决于编译器。但是9/10,它从最高有效端进行移位并导致位掉落。在OP的情况下,逻辑上是他的编译器选择的实现。 - Caladain
但是,为了论证,让我们再看一下 OP。对于有符号整数的位移结果(编译器如何处理),保存在无符号整数中。现在,如果符号位存储在最左边的位中,它将始终为零(因此我认为是正数?不确定编译器是否得到实现者的选择)。另一方面,如果符号位在最左边,并且编译器的实现在保留该符号位方面具有破坏性,您可能会得到意想不到的结果。(从有符号转换为无符号和不稳定的符号位) - Caladain

4

500被向右移位了4次。

x >> y在数学上表示为x / 2^y

因此500 / 2^4等于500 / 16。在整数除法中,结果为31


2

它使用整数除法将500除以16。

>>是一个右移操作符,它将n的二进制表示向右移动4次。这相当于将n除以2的4次方,即除以2^4=16。这是整数除法,因此小数部分被截断了。


2
应该提到16 = 2^4。 - vog

2

它将500的二进制位向右移动4位,同时丢弃最右边的位。

500 = 111110100 (二进制)

111110100 >> 4 = 11111 = 31


2

500的二进制表示为[1 1111 0100]
(4 + 16 + 32 + 64 + 128 + 256)

将其向右移动4位,你会失去最低的4位,结果为:
[1 1111]

即为1 + 2 + 4 + 8 + 16 = 31

你也可以用十六进制来查看它:

500(十进制)等于0x1F4(十六进制)。
然后向右移动4位,或者一个nibble
0x1F等于31(十进制)。


2

111110100是二进制中的500。将位向右移动,你会得到11111,这是二进制中的31。


1

C++有很好的类来模拟位级别上正在发生的事情

#include <bitset>
#include <iostream>

int main() {
    std::bitset<16> s(500);
    for(int i = 0; i < 4; i++) {
      std::cout << s << std::endl;
      s >>= 1;
    }

    std::cout << s
              << " (dec " << s.to_ulong() << ")"
              << std::endl;
}

1

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接