整数除法溢出 [英] Integer division overflows
问题描述
我一直在考虑整数(类型为int)的溢出,而在我看来除法可能会溢出。
I have been thinking about integer (type int) overflows, and it occurs to me that division could overflow.
示例:在当前平台上,我有
Example: On my current platform, I have
INT_MIN == -INT_MAX - 1
,因此
INT_MIN < -INT_MAX
,因此
INT_MIN / -1 > -INT_MAX / -1
,因此
INT_MIN / -1 > INT_MAX.
因此,除法(INT_MIN / -1)确实溢出。
Hence, the division ( INT_MIN / -1 ) does overflow.
所以,我有两个问题:
-
一个人可以写什么(跨平台的)C代码来防止除法溢出(对于(有符号的)int类型)?
What (cross-platform) C code could one write in order to prevent division overflows (for type (signed) int)?
什么保证(以C或C ++标准)可能有助于设计代码?
What guarantees (in C or C++ standard) might help to devise the code?
例如,如果标准保证我们拥有
For example, if the standard guarantees that we have either
INT_MIN == -INT_MAX - 1
或
INT_MIN == -INT_MAX,
然后显示以下代码
#include <limits.h>
/*
Try to divide integer op1 by op2.
Return
0 (success) or
1 (possibly overflow prevented).
In case of success, write the quotient to res.
*/
int safe_int_div(int * res, int op1, int op2) {
/* assert(res != NULL); */
/* assert(op2 != 0); */
if ( op1 == INT_MIN && op2 == -1 ) {
return 1;
}
*res = op1 / op2;
return 0;
}
推荐答案
什么保证(用C或C ++标准)可能有助于设计代码?
What guarantees (in C or C++ standard) might help to devise the code?
C使用3中的1指定整数形式:符号和大小,二进制补码或二进制补码。鉴于这些形式,只有溢出除以0和 INT_MIN / -1
的补数除法。
C specifies signed integer representation as using 1 of 3 forms: sign and magnitude, two’s complement, or ones’ complement. Given these forms, only division by 0 and two’s complement division of INT_MIN/-1
may overflow.
一个人可以写什么(跨平台的)C代码以防止除法溢出(对于(有符号的)int类型)?
What (cross-platform) C code could one write in order to prevent division overflows (for type (signed) int)?
int safe_int_div(int * res, int op1, int op2) {
if (op2 == 0) {
return 1;
}
// 2's complement detection
#if (INT_MIN != -INT_MAX)
if (op1 == INT_MIN && op2 == -1) {
return 1;
}
#endif
*res = op1 / op2;
return 0;
}
这篇关于整数除法溢出的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!