位移的目的是什么?

4
我在代码中发现了以下内容。
unsigned char A = 0xB9;
unsigned char B = 0x91;
unsigned char C = A << 3; // shift bits in A three bits to the left.
unsigned char D = B >> 2; // shift bits in B two bits to the right.

我知道它是位移,但它有什么作用,什么时候应该使用它呢?


如果对你没有任何意义,那么它就没有任何用处。只需忽略这段代码即可。 - leppie
1
这个问题太宽泛了,没有答案。加法的目的是什么?它是一种运算。 - Dave Hillier
2
是的,这对我来说并不重要,但我认为我应该了解它! - Kingfisher Phuoc
4
依我拙见,这是一个合理的问题。请关闭它,但需要给出比“不是一个真正的问题”更相关的理由。敬礼, - Junaid Qadir Shekhanzai
1
谢天谢地,在它被关闭之前,有人挤进来回答了。 - anton1980
6个回答

22

主要用途是当您使用特定位来定义较大项目的某个部分时。

以一个明显的例子为例,考虑一个32位数字,它保存颜色——每个颜色通道8位,分别对应红、绿、蓝色,另外8位则可能表示alpha值(指示此颜色/像素的透明度)。在十六进制下,这些数字看起来像:

AARRGGBB

(例如,每个分量均为两位数或8位)。

我们可以将这样的东西分解成组件,就像:

red = color & 0xff;
green = (color >> 8) & 0xff;
blue = (color >> 16) & 0xff;
alpha = (color >> 24) & 0xff;

反过来,我们可以将组件放在一起:

color = (alpha << 24) | (blue << 16) | (green << 8) | red;

在处理硬件时,你通常会像上面的颜色例子一样使用位操作。例如,你可能有一个16位寄存器,将其中5位用于一些事情,另外2位用于其他事情,6位用于第三个事情等等。当你想要更改其中之一时,你可以像上面的颜色例子一样:隔离表示一个字段的位,根据需要进行修改,然后将其与其他位重新组合。

另一个(完全不相关的)应用是哈希。这里我们通常没有类似的字段,但我们希望某些输入字节产生单个输出,使得输出的所有位都受到输入字节的影响。为了实现这一点,大多数人最终都要移位,以便每个输入字节都有至少一定的机会影响结果的不同部分。

我要补充的是,虽然相当多的旧代码使用位移操作来优化乘以或除以2的幂次方,但这对于现代硬件和编译器通常是浪费时间的。你会在现有代码中看到它,并应该理解它试图实现什么 - 但不要试图效仿它的示例。


有些人说使用位移操作比正常方式快一点?这是正确的吗? - Kingfisher Phuoc
3
@Kingfisher:正常的方式是什么?如果你指的是位移与乘除法,是的,位移指令可能比乘除法指令快——但当情况如此时,大多数编译器都能够为您执行这种优化。 - Jerry Coffin
我是不是读错了,还是第一个代码示例(按照原样编写)实际上是针对AABBGGRR而不是AARRGGBB的? - Monte Hurd
@MonteHurd:我认为这里没有足够的东西来说它是颜色。 - Jerry Coffin
3
准确地说,如果有人使用此示例来测试其位移理解(无论颜色如何,仅使用“a”、“r”、“g”和“b”表示相对字节位置),则按照现有代码的方式适用于AABBGGRR,而不是AARRGGBB。 - Monte Hurd

10

一个例子是单色位图,其中每个像素由一个单独的比特表示。假设你有一个圆形。

........
...oo...
..O..O..
.O....O.
.O....O.
..O..O..
...oo...
........

假设一个 . 用一个 0 位表示,而一个 O 则用一个 1 位表示,因此第二行的二进制表示为000110000,或者十进制表示为24。现在如果你想将圆形向右移动1像素,你需要将其表示中的位向右移动1位。

........
....oo..
...O..O.
..O....O
..O....O
...O..O.
....oo..
........
所以经过移位后,第二行现在是00001100(或十进制数12)。

4
+1指的是单色精灵卷轴滚动效果。现在我们看起来真的有些老了。 - StuartLC
从未想过这个。这一定是很流行的方式。 - chris

5

位移具有几个用途

  • 乘以或除以二的幂次方
  • 通过左[右]移后查找溢出[或下溢],检查最重要位或最不重要位是否设置(MSB或LSB)。
  • 弱加密形式。不是。

4
弱加密方式,真的吗? - Hasturkun
@Hasturkun:99%的第一次尝试编写密码都比XOR弱。 - leppie
@leppie:这是具有误导性的,因为位移运算也被用于所有常见的强加密算法,如DES和AES。 - MSalters

0

其中一个用途是通过整数次幂的2进行除法或乘法。


快速?与常规算术相比还是什么? - Luchian Grigore
在这种情况下,我会建议我的前任老板立即降低他的薪水。 - mathematician1975
请参考此链接 - https://dev59.com/QWw15IYBdhLWcg3w3ffN - Luchian Grigore
@LuchianGrigore 感谢您提供的链接。我一直以为它更快,现在已经编辑了答案,删除了它更快的暗示。 - mathematician1975
@MrLister 可能是这样,但如果可以的话,除法很可能已经被优化为移位。 - Luchian Grigore
显示剩余2条评论

0

位移或位模式用于压缩文件。有些人也用它进行加密。


0

移位有很多用途,远远超出了此处可以解释的范围。一个很好的例子是在组装代码时将值移动到正确的位置。同时,左移1位相当于将值乘以2,只是速度更快。同样地,右移相当于除以2。


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