在《C陷阱和缺陷》里有谈到整数溢出的问题。里面说到,无符号整数是不存在“溢出的,有符号整数才会”溢出”。
一般理解,溢出就是运算结果超出了本身的表示范围。
那么其实无符号整数也是会溢出的。之所以说没有所谓“溢出”一说,是因为无符号运算是明确定义的,它的结果是按2的n次方为模。即使溢出了,其结果也是可预见的。
然而,有符号运算就不是如此了。对于有符号运算而言,如果溢出,结果是未定义的。其结果和编译器或平台有关。
<pre name="code" class="cpp">比如
unsigned short a=0xffff;
unsigned short b=1;
unsigned short c=a+b; //c=0
变量c的结果是确定的。
short a=0x7fff;
short b=2;
short c=a+b; //c的结果不确定
不要想当然,认为c会变为负数。运算a+b发生溢出,作任何假设都是不可靠的。
a和b是有符号非负整数。
if(a+b<0)
overflow();
这种检测溢出的方式是没有效果的。
if(a>INT_MAX-b)
overflow();
这种方式才是可行的。
if((unsigned int)a+(unsigned int)b>INT_MAX)
overflow();
这种方式也可以。