加法溢出:
无符号整数溢出判断较简单
boolean uadd_ok(unsigned x,unsigned y){
unsigned sum=x+y;
return sum>=x;
}
有符号整数溢出的时候只存在正溢出和负溢出两种情况,即两正数相加得到一个负数或两负数相加得到一个正数。
public static boolean tadd_ok(int x,int y){
int sum=x+y;
boolean neg_over=x<0&&y<0&&sum>=0;
boolean pos_over=x>=0&&y>=0&&sum<0;
return !neg_over&&!pos_over;
}
需要注意的是
boolean tadd_ok(int x,int y){
int sum=x+y;
return (sum-x==y)&&(sum-y==x);
}
这种方法是无法判断溢出的,因为x+y无论是否溢出,x+y-y始终等于x是因为补码加上形成一个阿贝尔群,由阿贝尔群的交换律和结合律有(x+y)-x==y。
减法溢出
减去一个数可以理解为加上这个数的负数,于是
int tsub_ok(int x,int y){
return tadd_ok(x,-y);
}
但是这样写是存在一定问题的,没有考虑TMIN(即取值范围的最小值,32位时为-2147483648),TMIN没有相反数,所以需要考虑y为TMIN的情况。其实当y==TMIN时,只有在x>=0的情况下x-y才会溢出
int tsub_ok(int x,int y){
if(y==TMin)
{
if(x>=0)
return false;
else
return true;
}
else
return tadd_ok(x,-y);
}
乘法溢出
boolean tmult_ok(int x,int y){
int p=x*y;
if(p/y!=x)
return false;
else
return true;
}
网友评论