int除以unsigned int导致溢出问题

9
我尝试将int除以unsigned int,但是得到了意外的结果:
int b;
unsigned int c;
int res;
float res_f;

b = -25;
c = 5;

res = b / c;   // res = 858993454
res_f = b / c; // res_f = -5.000000

相同的方法对于“+”、“-”和“*”都可以正常工作,但是对于“/”则失败了。我在这里错过了什么?
附注:
已在不同的编译器上进行了测试,结果相同。
1个回答

16

假设这是C语言或类似的语言(例如Objective C),修改为:

res = b / c;

发送至:

res = b / (int)c;
Explanation: b被转换为unsigned int,根据C语言混合表达式的类型转换规则。在这个过程中,b从-25溢出到0xFFFFFFE7 == 4294967271。然后你得到一个unsigned int结果为4294967271 / 5U = 858993454U,然后被隐式地转换回一个int(在这一步没有溢出,因为结果在有符号和无符号32位整数的范围内)。
顺便说一下,float结果应该是相同的,在float的精度限制下(我得到858993472.0)。我对于你在这种情况下得到-5.0感到惊讶。

1
这就是为什么具有隐式类型转换的语言是邪恶的。如果你不想遇到这样的问题,就使用一个真正强大的类型系统的语言,比如Ada。 - T.E.D.
1
如果上下文需要,将c设置为unsigned short也可以。 - aaz

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接