【发布时间】:2016-02-05 02:24:32
【问题描述】:
假设我想将x 乘以(3/8)。所以我可以使用移位操作得到结果如下(结果应该向零舍入):
int Test(int x) {
int value = (x << 1) + x;
value = value >> 3;
value = value + ((x >> 31) & 1);
return value;
}
所以我将在Test(11) 中有4,在Test(-9) 中有-3。问题是,因为我先做乘法,所以在某些范围内会溢出,在这种情况下我不会得到正确的值:
Test(0x80000000) // returns -268435455, but it should be -268435456
我该如何解决这个问题?
【问题讨论】:
-
你已经在几天前发布了这个问题。我(和其他人)告诉过你你调用 undefined 和 implementation defined behavior。并且溢出还会调用未定义的行为,所以所有的赌注都被取消了。
-
您需要使用大于
int的变量,例如long假设long在您的系统上有更多位。或者您可以将int拆分为两个ints,每个都有一半的位,然后进行数学运算。 -
@user3386109:
long在 POSIX64 上只有更多位,并且不是真正可移植的。最好使用固定宽度类型。这些也有明确定义的表示,因此有符号/无符号的转换行为。 -
@Olaf 注意:除了 POSIX64 之外,许多系统的
long都比int宽:嵌入式平台、DOS 等。 -
@Olaf 感谢您再次提及。请注意,未定义的行为并没有真正改变我的问题,这也不是同一个问题。我仍然想处理这个溢出(请阅读标题)。此外,由于我问了这个问题,这仅意味着您以前的 cmets 没有帮助。
标签: c bit-manipulation overflow