溢出问题

seal1985 2009-05-10 06:45:06
溢出
最近在看深入浅出计算机系统,其中有关溢出有个问题
int main()
{
int val ;

val = 2147483647 > -2147483647 - 1;
return 0;
}

int main()
{
int val ;

val = 2147483647 > -2147483648;
return 0;
}

第一个能得到正确结果,而第二个会因为发生溢出得到错误结果,why?
...全文
426 31 打赏 收藏 转发到动态 举报
写回复
用AI写文章
31 条回复
切换为时间正序
请发表友善的回复…
发表回复
风老二 2009-06-08
  • 打赏
  • 举报
回复
好像在那本书上看过
二进制表示整数时为了避免逻辑上的-0,所以其表达值界限为 -(s+1)->0->s
mu_yang 2009-05-15
  • 打赏
  • 举报
回复
[Quote=引用 10 楼 xempo 的回复:]
哦!My God。
你们都错了,貌似我来迟了。
应该是int 没有-2147483648这个值——溢出了。
而有-2147483647这样的值,而-214748364 -1 并不等于-2147483648。
[/Quote]
[Quote=引用 27 楼 xempo 的回复:]
多举两个例,说明我在10楼所说的。
补:打印的字串末尾加'\n'好看一点。
[/Quote]


printf("flow:%d",-2147483648);
printf("-1:%d",-2147483647-1);
printf("-10:%d",-2147483647-10);
printf("-100:%d",-2147483647-100);


在我的编译器上输出
flow:-2147483648
-1:-2147483648
-10:2147483639
-100:2147483549
请按任意键继续. . .

后两个溢出了
但前两个
我怎么看不出溢出了呢
xempo 2009-05-15
  • 打赏
  • 举报
回复
[Quote=引用 29 楼 xempo 的回复:]
这样,以上的程序应该象如此的吧。
[/Quote]
这样,“楼主”的程序应该没错误的。
xempo 2009-05-15
  • 打赏
  • 举报
回复
回28楼:
我没记整数在计算机的极限值具体是多少,只道是楼主给出的-2147483648是溢出,而最小极限是-2147483647。
28的提点,我回家细看了一下,-2147483648是存在的。这样一来,那是楼主故意给所有的过客以“皇帝的新装”了。
我原想,楼主的本意是考-2147483649吧!
int main()
{
int val ;

val = 2147483647 > -2147483648 - 1;
return 0;
}

int main()
{
int val ;

val = 2147483647 > -2147483649;
return 0;
}
这样,以上的程序应该没错误的。
告诉morris88兄,今晚买一件衣服去,别穿着皇帝的新装(光着膀子)上网了(天气热的缘故)。
xempo 2009-05-14
  • 打赏
  • 举报
回复
[Quote=引用 24 楼 mu_yang 的回复:]
23楼想说明什么?
[/Quote]多举两个例,说明我在10楼所说的。
补:打印的字串末尾加'\n'好看一点。
mu_yang 2009-05-13
  • 打赏
  • 举报
回复
[Quote=引用 25 楼 caodaxia 的回复:]

int数据占2B的存储空间时,其取值范围为(-2147483648,2147483647)而非(-2147483647,2147483647)
这是有正数与负数的存储方式不一样决定的
[/Quote]

你确定?
caodaxia 2009-05-13
  • 打赏
  • 举报
回复

int数据占2B的存储空间时,其取值范围为(-2147483648,2147483647)而非(-2147483647,2147483647)
这是有正数与负数的存储方式不一样决定的
mu_yang 2009-05-13
  • 打赏
  • 举报
回复
23楼想说明什么?
xempo 2009-05-12
  • 打赏
  • 举报
回复

printf("flow:%d",-2147483648);
printf("-1:%d",-2147483647-1);
printf("-10:%d",-2147483647-10);
printf("-100:%d",-2147483647-100);


Try !


mu_yang 2009-05-11
  • 打赏
  • 举报
回复
在 2147483647 > -2147483647 - 1 这个表达式中
2147483647 和 1 是 int 类型的常量
因此表达式 -2147483647 (注意这不是一个int类型的常量,而是 - 与 2147483647 构成的表达式)
也是int类型的
同理
-2147483647 - 1 也是int类型的
这样两个int类型的量 2147483647 与 -2147483647 - 1 的 > 运算的结果为1

而在 val = 2147483647 > -2147483648 这个表达式中
2147483647 是int
2147483648并不是一个int类型的常量
(视编译环境)这最有可能是一个unsigned int 类型的常量
这样表达式 -2147483648 也是一个 unsigned int
而且2147483647 也必须隐式地转化为(unsigned int)2147483647
对于unsigned int
显然 7FFF FFFF < 8000 0000

结论是
不是优先级的问题
是数据类型的问题

许多人最容易犯的一个错误是
把-2147483648 这种东东当做常量
实际上-2147483648 是表达式
2147483648 才是常量
常量是没有负数的
mu_yang 2009-05-11
  • 打赏
  • 举报
回复
在 2147483647 > -2147483647 - 1 这个表达式中
2147483647 和 1 是 int 类型的常量
因此表达式 -2147483647 (注意这不是一个int类型的常量,而是 - 与 2147483647 构成的表达式)
也是int类型的
同理
-2147483647 - 1 也是int类型的
这样两个int类型的量 2147483647 与 -2147483647 - 1 的 > 运算的结果为1

而在 val = 2147483647 > -2147483648 这个表达式中
2147483647 是int
2147483648并不是一个int类型的常量
(视编译环境)这最有可能是一个unsigned int 类型的常量
这样表达式 -2147483648 也是一个 unsigned int
而且2147483647 也必须隐式地转化为(unsigned int)2147483647
对于unsigned int
显然 7FFF FFFF < 8000 0000

结论是
不是优先级的问题
是数据类型的问题

许多人最容易犯的一个错误是
把-2147483648 这种东东当做常量
实际上-2147483648 是表达式
2147483648 才是常量
常量是没有负数的
qq316921615 2009-05-11
  • 打赏
  • 举报
回复
给个一致的意见呗~~~~~
alexhilton 2009-05-11
  • 打赏
  • 举报
回复
数越界了
matrixcl 2009-05-11
  • 打赏
  • 举报
回复


val = 2147483647 > -2147483648;


warning C4146: 一元负运算符应用于无符号类型,结果仍为无符号类型


貌似2147483648被当成无符号数了
seal1985 2009-05-11
  • 打赏
  • 举报
回复
[Quote=引用 14 楼 lichunqi24 的回复:]
各楼的的解释都不是很准确,我在VC6++上运行了楼主的程序,结果
确实如楼主所述,但编译时提示有一个警告:
unary minus operator applied to unsigned type, result still unsigned
以上警告针对:val=a>-2147483648; 这个语句。
意思好像是-2147483648被认为是无符号数,结果也是无符号数;
另外常量可以是负数;

我在调试中又遇到了另外的问题,请看如下程序:
int main()
{
int val,a,b;
a=214…
[/Quote]
当把-2147483648赋给变量b,然后在进行:val=a>b运算,此时a=2147483647,是int型,
而b=-2147483648,首先将2147483648看成unsigned,从而-2147483648的结果也是unsigned,-2147483648的二进制0X80000000,由于b是int,最终结果是由0X80000000转化来的int结果,即b=-2147483648, 在val=a>b中,a,b都是
int,最终结果是int,不会发生溢出,所以得到1。不知道是不是这样子。
mu_yang 2009-05-11
  • 打赏
  • 举报
回复
此外
对是否真的发生了溢出
我是很怀疑的
我认为没有发生溢出

实际上
-(unsigned)2147483648 的确等于 (unsigned)2147483648
mu_yang 2009-05-11
  • 打赏
  • 举报
回复
[Quote=引用 16 楼 seal1985 的回复:]
对你说的加-号变表达式有点困惑,看完你的说法,我想到一种解释:
val = 2147483647 > -2147483647 - 1; 2147483647和1首先被看成int常量,由于val也是int,所以最终的结果是int,
-2147483647 - 1的结果可以表示成int型-2147483648。所以val=1;
val = 2147483647 > -2147483648; 2147483648首先被看成unsigned int,所以最终结果是unsigned,将int型
-2147483648,其补码表示为0x80000000,转换为unsigned得到2147483648,所以最终的比较结果为0。
不知道可不可以这样解释 [/Quote]

"-" 是一个运算符
因此 -2147483647 是一个表达式

你说的“由于val也是int”,我不赞成
你会发现,哪怕val是char类型,结果也是如此
2147483647 > -2147483647 - 1 的值与var的类型无关

其余的我基本同意

seal1985 2009-05-11
  • 打赏
  • 举报
回复
[Quote=引用 13 楼 mu_yang 的回复:]
在 2147483647 > -2147483647 - 1 这个表达式中
2147483647 和 1 是 int 类型的常量
因此表达式 -2147483647 (注意这不是一个int类型的常量,而是 - 与 2147483647 构成的表达式)
也是int类型的
同理
-2147483647 - 1 也是int类型的
这样两个int类型的量 2147483647 与 -2147483647 - 1 的 > 运算的结果为1

而在 val = 2147483647 > -2147483648 这个表达式中
2147483647 是int
2147483648并不是一个int…
[/Quote]
对你说的加-号变表达式有点困惑,看完你的说法,我想到一种解释:
val = 2147483647 > -2147483647 - 1; 2147483647和1首先被看成int常量,由于val也是int,所以最终的结果是int,
-2147483647 - 1的结果可以表示成int型-2147483648。所以val=1;
val = 2147483647 > -2147483648; 2147483648首先被看成unsigned int,所以最终结果是unsigned,将int型
-2147483648,其补码表示为0x80000000,转换为unsigned得到2147483648,所以最终的比较结果为0。
不知道可不可以这样解释
xempo 2009-05-11
  • 打赏
  • 举报
回复
偶过小桥见鱼舞,始觉浮生有半日。
  • 打赏
  • 举报
回复
各楼的的解释都不是很准确,我在VC6++上运行了楼主的程序,结果
确实如楼主所述,但编译时提示有一个警告:
unary minus operator applied to unsigned type, result still unsigned
以上警告针对:val=a>-2147483648; 这个语句。
意思好像是-2147483648被认为是无符号数,结果也是无符号数;
另外常量可以是负数;

我在调试中又遇到了另外的问题,请看如下程序:
int main()
{
int val,a,b;
a=2147483647;
b=-2147483647;
val=a>b-1;
printf("%d\n",val);
val=a>-2147483648;
b=b-1;
printf("%d\n",b);
printf("%d\n",val);
val=a>b;
printf("%d\n",val);
return 0;
}
运行结果为:
1
-2147483648
0
1
当把-2147483648赋给变量b,然后在进行:val=a>b运算
就能得到有效地结果,请各位分析一下这是为什么
加载更多回复(11)

69,369

社区成员

发帖
与我相关
我的任务
社区描述
C语言相关问题讨论
社区管理员
  • C语言
  • 花神庙码农
  • 架构师李肯
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧