我正在研究static_casting long double double时gcc和gdb的奇怪行为。我有类似下面的代码:gdb中的C++ static_cast返回与gcc不同的结果
const double xDelta = 60.0;
int xSplits = 3;
const long double xStepL = static_cast<long double>(xSplits)/xDelta;
const double xStep = static_cast<double>(xStepL);
基本上它分3/60,所以结果应该是0.05。当以简单的double
值运行时,xStep
的值是0.050000000000000003
,所以决定使用12字节的更高精度的long double
。上例中xStepL
的值为0.05000000000000000000067762635780344
。当将此值重新输入到double
时,实际上它又是0.050000000000000003
。但是,使用gdb检查数值时,它会打印以下内容:
(gdb) p xStep
$1 = 0.050000000000000003
(gdb) p static_cast<double>(xStepL)
$2 = 0.049999999999999996
任何想法为什么结果不同?我真的希望它成为第二个。任何人都知道如何做到这一点?
顺便说一下,我正在使用GCC 4.3.4和GDB 7.2.50。
'0.05'不能用二进制浮点表示,所以实际值将是'0.050000000000000003'('0x1.999999999999ap-5')或'0.049999999999999996'('0x1.9999999999999p-5')之一。越大的值越接近'0.05'('0x1.9 ... ap-5'),所以你应该更喜欢这个值。 – ecatmur 2012-08-02 13:21:18
该值稍后被乘以并转换为整数作为内存访问的偏移量。不幸的是,在这个特殊情况下(这是一个测试用例和绝对边界),它会产生变化并超出可用内存。 – t1mg 2012-08-02 13:33:00
内存问题的可能解决方案包括测试边界和钳位(但是这会在代码中引入分支),或者在内存块的末尾添加副本 - 但只有在访问权限是只读的情况下才有效。 – 2012-08-03 00:02:53