我一直在看有关掩码的帖子,但仍然不知道如何从 C 中的数字中提取某些位。
说如果我们有一个int number 0001 1010 0100 1011
,那么它的十六进制表示是对的x1a4b
吗?如果我想知道第 5 到第 7 个数字,101
在这种情况下,我应该使用int mask= 0x0000 1110 0000 0000, int extract = mask&number
吗?
另外我如何检查它是否是101
?我想==
不会在这里工作......非常感谢!
我一直在看有关掩码的帖子,但仍然不知道如何从 C 中的数字中提取某些位。
说如果我们有一个int number 0001 1010 0100 1011
,那么它的十六进制表示是对的x1a4b
吗?如果我想知道第 5 到第 7 个数字,101
在这种情况下,我应该使用int mask= 0x0000 1110 0000 0000, int extract = mask&number
吗?
另外我如何检查它是否是101
?我想==
不会在这里工作......非常感谢!
屏蔽是通过将除您想要的位之外的所有位设置为 0 来完成的。假设您有一个 8 位变量,并且您想检查 5 位是否为 1。假设您的变量是00101100
. 为了屏蔽所有其他位,我们使用 & 运算符将除第 5 个 1 之外的所有位设置为 0:
00101100 & 00010000
现在,除了第 5 位之外的每一位,右侧字节的位将为 0,因此 & 运算的结果将为 0。但是,对于第 5 位,右侧的值是a 1,因此结果将是从左字节开始的第 5 位的值 - 在本例中为 0:
现在要检查这个值,你必须将它与某些东西进行比较。为此,只需将结果与右侧的字节进行比较:
result = (00101100 & 00010000) == 00000000
为了概括这一点,您可以简单地通过左移 00000001 来从左侧字节中检索任何位,直到获得所需的位。下面的函数实现了这一点:
int getBit(char byte, int bitNum)
{
return (byte & (0x1 << (bitNum - 1)))
}
这适用于任何大小的变量,无论是 8、16、32 还是 64(或其他任何大小)。
假设 gcc 扩展0b
定义二进制文字:
int number = 0b0001101001001011; /* 0x1a4b */
int mask = 0b0000111000000000; /* 0x0e00 */
/* &'ed: 0b0000101000000000; 0x0a00 */
int extract = mask & number; /* 0x0a00 */
if (extract == 0b0000101000000000)
/* or if 0b is not available:
if (extract == 0x0a00 ) */
{
/* success */
}
else
{
/* failure */
}
你需要掩饰和转移。移动您要比较的值,或者您要比较的值。我发现通过改变你要比较的价值来更容易思考。因此,如果您尝试提取第 5 到第 7 位(从左侧开始),则向右移动9 位(16-7),以便第 7 位现在是最右边,然后应用 0x7(二进制中的 111)作为掩码只得到最右边的三个二进制数字
int i = 0x1A4B;
if (((i >> 9) & 0x07) == 0x05) { // 0x05 = 101 in binary
//do what you need to
}
首先,二进制中的数字(通常)从右边(第 10 位和第 12 位)开始计算,或者说是第 5 位和第 7位最高有效数字。
int mask = 0x0E00; // 0000 1110 0000 0000;
int extract = mask & number;
结果是:
extract = 0000 1010 0000 0000
你可以做
if (extract == 0x0A00 /*0000 1010 0000 0000*/){}
测试,或:
if (( extract >> 9 ) == 0x05){}
if 中的两个语句都将使用您的样本编号返回 true。
通常戴着面具,你会发现自己在测试一个数字。你可以使用这样的函数来测试它:
bool digit_value( unsigned int number, unsigned int digit)
{
return (1 << digit) & number;
}
int main()
{
unsigned int number = 0x1A4B;
int should_be_three = 0;
should_be_three += digit_value(number, 10);
should_be_three += !digit_value(number, 11);
should_be_three += digit_value(number, 12);
printf("%s", (should_be_three == 3?"it worked":"it didn't work"));
return 0;
}
我应该使用int mask= 0x0000 1110 0000 0000
,int extract = mask&number
吗?- 是的,你可以这样做。
另外,我怎样才能检查它是否是101
?当然你可以检查这个 -
0000 1010 0000 0000
这是1280
在int
.
extract== 1280
逐个检查位可能更简单,而不是一次检查所有位。首先,您为感兴趣的位创建掩码:
int fifthBitMask = 1 << 4;
int fifthBitResult = number & fifthBitMask;
int seventhBitMask = 1 << 6;
int seventhBitResult = number & seventhBitMask;
现在,您可以将结果与零或掩码进行比较。可以省略与零的比较,因此您可以使用简单的 if:
if (fifthBitResult && seventhBitResult)
{
//your code here
}
此外,您可以与口罩进行比较。在操作 & 之后,结果中将只设置掩码中设置的位。所以,它可能是这样的: if (fifthBitResult == FifthBitMask && SevenBitResult == SevenBitMask) { // 你的代码在这里 }
因此,如果运算结果等于掩码,您可以通过一个操作来做到这一点:
int mask = 0x5 << 4; // 0x5 is hex representation of 101b
int result = number & mask;
if (result == mask)
{
// your code here
}
首先,您对 7-6-5 位的计算是不正确的。您说它是 101 但它是 010(对于 x1a43)其次,要获取这些位(这些位表示的值),您应该这样做&0xE0
。
int my_bits_from_5to7 = number & 0xE0;