Visual C++ 6 的 BUG:
davies 发表于 2006 年 08 月 13 日
意外的发现一个Visual C++ 6 的bug :
调试C++代码时,用 Watch 察看一个表达式的值,如果该表达式中同时有 __int64 和 double 两种数值类型,其结果就会错得离谱,比如 __int64(0)+1.0,用 watch 查看的值竟然为 460718241880017408 !
这个古怪结果的十六进制表示为 0x3ff0000000000000。根据某某标准,双精度浮点数1.0用8个字节来表示,上面那个古怪结果正是1.0。可以通过如下方法查看1.0的表示方法:
double a = 1.0;
__int64 *a64 = (___int64*)a;
用 watch 查看 *a64 的值,并用十六进制表示,就可以看到是0x3ff0000000000000。
原来是用 watch 查看表达式时对 double 和 __int64 之间的类型转换有问题,由于它们是具有相同精度的,都是8个字节,不知道是从__int64转到double,还是从double转到__int64,居然就不做类型转换了,直接把double类型当作__int64类型来处理,所以出错。
我们来继续发掘,查看表达式 1.0+__int64(10)的值,居然是 1.0 ! 结合上面的例子可以看出,它是把后面一种数据类型直接当作前一种数据的类型来处理,而不做任何转换。10的十六进制表示为 0x000000000000000a,当作double类型的话,就是0了。
不过不用担心,这个bug并不影响程序的运行,代码执行结果还是正确的。
再来看看 Visual C++ 2005 的表现,不管是1.0+__int64(1) 还是 __int64(1)+1.0,其结果都是2.0,类型为double,终于做了正确的处理。Visual C++ 2003中没有试过,不知道有没有该问题。
网友留言:
2. 发表于 2006 年 08 月 16 日 12:13 a.m.
不是不知道,一试下一跳
3. 发表于 2006 年 11 月 16 日 9:47 a.m.
我试了,不是这样。
我打了sp6补丁!
4. 发表于 2006 年 11 月 16 日 9:56 a.m.
可能在sp6中已经将这个Bug修正,不错
1. 发表于 2006 年 08 月 15 日 4:53 p.m.
还有这种问题,KK。