移位超过8位 - 导致输出错误

时间:2014-07-09 20:06:34

标签: c++ hex

我正在尝试执行此操作,并且我得到了错误的输出。

signed char temp3[3] = {0x0D, 0xFF, 0xC0};
double temp = ((temp3[0] & 0x03) << 10) | (temp3[1]) | ((temp3[2] & 0xC0) >> 6)

我正在尝试形成一个12位数字。得到0x0D的最后2位,0xFF的全部8位和0xC0的前2位形成二进制数(011111111111)= 2047,但是我得到-1。当我打破第一个掩码并移动10时,我得到0.我不知道这是否是我的问题,试图将8位字符移位10位。

2 个答案:

答案 0 :(得分:0)

当比特蹒跚时,总是使用无符号数字

将数组更改为unsigned char

为每个常量添加“U”后缀,因为默认情况下每个常量都是 signed 整数。

BTW,对于有符号整数,右移是未定义的 实现定义

根据评论,将“未定义”更改为“已定义实施”。

答案 1 :(得分:0)

您需要解决一些问题。

首先,c ++没有12位数字。你可以拥有的最好的是16位。顶部位表示二进制补码形式。

您还需要非常小心地移动要移动的数字类型。在您的示例中,您将使用超过8位的字符串进行移位。由于char只有8位,所以你将它归零。

以下示例给出了正确的实现(对于带符号的12位数字)。毫无疑问,效率更高。

// shift in top 2 bits
signed short test   =  static_cast<signed short>(temp3[0] & 0x03) << 10 ;

// shift in middle 8 bits
test   |=  (static_cast<signed short>(temp3[1]) << 2)  & 0x03FC;
// rightshift, mask and append lower 2 bits
test   |=  (static_cast<signed short>(temp3[2]) >> 6)  & 0x0003;
// sign extend top bits from 12 bits to 16 bits
test |= (temp3[0] & 0x02) == 0 ? 0x0000 : 0xF0000;