c# - 获取特定位并获取 ushort 值的前 14 位

c# - Get Specific Bit and Get first 14 bits of a ushort value

读完位 shifting/masking 上的所有问题和答案后,我简直无法理解它。我只是不了解它在基本层面上是如何工作的。我已经能够通过使用 BitArray 和 BitConverter 来实现各种技术,但我真的很想更好地理解位shifting/masking。

我的具体需求是:

我有一个短裤:0x810E (33038)

使用位 shifting/masking,我想知道如何:

正如我所说,我能够使用 BitArray 执行这些任务,这是我获得正确结果的方式,但我想了解如何使用位 shifting/masking 执行这些操作。

如有任何帮助,我们将不胜感激。

屏蔽单个位

你可能知道,ushort是一个16位的值,所以你给定的数字0x810E也可以写成

‭10000001 00001110‬

因为ushort没有移位运算符,所以值先转换为int.

所以,如果你想得到第15位,你可以取一个位

000000000 0000000 00000000 00000001

向左移动14次(右边填0

00000000 00000000 01000000 00000000

并且您已经创建了一个 位掩码

现在,如果您将掩码和值与按位组合 and,您将仅获得第 15 位的值:

  ‭00000000 00000000 10000001 00001110‬
& 00000000 00000000 01000000 00000000
= 00000000 00000000 00000000 00000000

又是0。要访问此位,您必须将整个结果向右移动 14 次,然后 cast 将其转换为 ushort.

这可以用下面的代码表示:

ushort value_15 = (ushort)(((1 << 14) & value) >> 14);

我们可以做得更好吗?

虽然这种做法看似正确,但是还有更简单的做法:将原值右移14次 (结果为 00000000 00000000 00000000 00000010,左侧填充 0)并执行简单的按位 &1:

  00000000 00000000 00000000 00000000 00000000 00000010 
& 00000000 00000000 00000000 00000000 00000000 00000001
= 00000000 00000000 00000000 00000000 00000000 00000000

这导致 C# 在:

ushort value_15 = (ushort)((value >> 14) & 1);

所以你避免了一次额外的转变,即使使用 有符号数(因为用于符号的最高位通过移位保持不变)。

屏蔽位范围

要屏蔽一个比特范围,你所要做的就是改变你的掩码。因此,要获取低 14 位的值,您可以使用 mask

  00000000 00000000 ‭10000001 00001110‬
& 00000000 00000000 00111111 11111111
= 00000000 ‭00000000 00000001 00001110

C#中可以用

表示
ushort first14bits = (ushort)((0xFFFF >> 2) & value);

其中(0xFFFF00000000 00000000 11111111 11111111)。