Vis*_*hal 7 c integer bit-manipulation
仅使用:
! ~ & ^ | + << >>
Run Code Online (Sandbox Code Playgroud)
我需要找出一个带符号的32位整数是否可以表示为16位,2的补码整数.
我的第一个想法是分离MSB 16位和LSB 16位,然后使用掩码和最后16位,所以如果它不为零,它将无法表示,然后使用该数字来检查MSB位.
我需要编写的函数示例是:fitsInShort(33000)= 0(无法表示)和fitsInShort(-32768)= 1(可以表示)
如果32位数字在[-32768,+ 32767]范围内,那么17个msbs将全部相同.
这是一个蹩脚的方式来判断一个3位数是全是1还是全零只使用你的操作(我假设你不允许条件控制结构,因为它们需要隐式逻辑运算):
int allOnes3(int x)
{
return ((x >> 0) & (x >> 1) & (x >> 2)) & 1;
}
int allTheSame3(int x)
{
return allOnes3(x) | allOnes3(~x);
}
Run Code Online (Sandbox Code Playgroud)
我会告诉你扩展/改进这个概念.
bool fits16(int x)
{
short y = x;
return y == x;
}
Run Code Online (Sandbox Code Playgroud)
开个玩笑:)这是真正的答案,假设int是32位,short是16位和2的补码represantation:
编辑:请参阅最后一次编辑以获得正确答案!
bool fits16(int x)
{
/* Mask out the least significant word */
int y = x & 0xffff0000;
if (x & 0x00008000) {
return y == 0xffff0000;
} else {
return y == 0;
}
}
Run Code Online (Sandbox Code Playgroud)
如果没有if语句我应该这样做:
return (
!(!(x & 0xffff0000) || !(x & 0x00008000)) ||
!((x & 0xffff0000) || (x & 0x00008000))
);
Run Code Online (Sandbox Code Playgroud)
编辑:奥利是对的.我不知何故以为他们被允许了.这是最后一次尝试,并附有解释:
我们需要17个最重要的位x是全部或全部为零.所以让我们从屏蔽其他位开始:
int a = x & 0xffff8000; // we need a to be either 0xffff8000 or 0x00000000
int b = a + 0x00008000; // if a == 0xffff8000 then b is now 0x00000000
// if a == 0x00000000 then b is now 0x00008000
// in any other case b has a different value
int c = b & 0xffff7fff; // all zeroes if it fits, something else if it doesn't
return c;
Run Code Online (Sandbox Code Playgroud)
或者更简洁:
return ((x & 0xffff8000) + 0x8000) & 0xffff7fff;
Run Code Online (Sandbox Code Playgroud)