右位移在C中添加1到unsigned int的开始

问题描述 投票:0回答:2

我试图移动一个16位地址来获取C中的缓存模拟器的设置ID,但是当我尝试向右移位时,我的数字会增加1。

我的号码为0010100010011001.然后我转到左边的3位数,得到0100010011001000.到目前为止一切顺利。然而,我然后尝试转移到正确的6位数,最后得到0000010100010011而不是0000000100010011.我的所有整数都是无符号的,当我尝试移位时它只增加1。

我尝试和转移的代码如下。在我的例子中,tag_size是3,b是6。

    unsigned int temp = addr << tag_size;
    unsigned int temp1 = temp >> b;
    unsigned int setid = temp1 >> tag_size;
c bit-shift
2个回答
1
投票

这一天,16位ints并不常见。您可以尝试将变量定义为short,通常为16位。这一切都取决于您使用的机器。如果要查找16位整数,也可以使用uint16

看起来问题可能是因为你正在使用的unsigned int实际上不是16位,就像Christian Gibbons在评论中提到的那样。当你将0010100010011001移动到左边的3位数时,你最终会得到10100010011001000,最左边的1个没有像你期望的那样被移除16位整数,那么当你再次向右移动时你会得到你没想到的加1。

您可以将代码更改为此代码,它应该按照您最初的预期工作:

uint16_t temp = addr << tag_size;
uint16_t temp1 = temp >> b;
uint16_t setid = temp1 >> tag_size;

0
投票

你应该使用一个掩码并选择你感兴趣的位;例如:

unsigned int temp = (addr << tag_size) & 0xffffu; // keep 16 low bits
unsigned int temp1 = temp >> b;
unsigned int setid = temp1 >> tag_size;

如果我理解你所追求的是什么,那么同样的事情就可以实现

unsigned int temp = addr & (0xffffu >> tag_size); // keep 16 low bits
unsigned int setid = temp >> b;

要么

unsigned int temp = (addr << tag_size) & 0xffffu; // keep 16 low bits
unsigned int setid = temp >> (b + tag_size);

这使得代码独立于unsigned int大小,C保证至少为16位。

© www.soinside.com 2019 - 2024. All rights reserved.