std :: pow在32位和64位应用程序中产生不同的结果 [英] std::pow produce different result in 32 bit and 64 bit application

查看:111
本文介绍了std :: pow在32位和64位应用程序中产生不同的结果的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我发现某些复杂计算的结果不匹配。当我彻底观察到中间结果时,其std :: pow函数会造成这种不匹配。
以下是输入/输出。

I have found the mismatch in the result of some complex calculations. When i thoroughly observed the intermediate results, its the std::pow function which creates that mismatch. Below are the inputs/output.

long double dvalue = 2.7182818284589998;
long double dexp = -0.21074699576017999;
long double result = std::powl( dvalue, dexp); 




64位->结果= 0.80997896907296496和32位->结果=
0.80997896907296507

64bit -> result = 0.80997896907296496 and 32bit -> result = 0.80997896907296507

我正在使用VS2008。
我尝试了pow函数的其他变体,该函数需要long double和return long double,但仍然看到相同的区别。

I am using VS2008. I have tried with other variation of pow function which takes long double and return long double, but still see the same difference.

double pow(double base,double exponent);

long double powl(long double base,long double exponent) ;

我已阅读以下信息:


英特尔x86处理器内部使用80位扩展精度,而
double通常为64位宽。不同的优化级别会影响
来自CPU的浮点值保存到内存中的频率以及
因此从80位精度四舍五入到64位精度。另外,
使用long double类型,通常在gcc上为80位宽,为
,以避免从80位精度舍入到64位精度。

Intel x86 processors use 80-bit extended precision internally, whereas double is normally 64-bit wide.Different optimization levels affect how often floating point values from CPU get saved into memory and thus rounded from 80-bit precision to 64-bit precision. Alternatively, use the long double type, which is normally 80-bit wide on gcc to avoid rounding from 80-bit to 64-bit precision.

有人可以让我清楚地理解这种差异以及克服这种差异的方法。

Could someone make me clearly understand the difference and ways to overcome this difference.

推荐答案

可能发生的情况是32位构建正在使用80位FPU寄存器进行计算,而64位构建正在使用使用64位值的SIMD操作,这会导致轻微的差异。请注意,两个答案都同意14位小数,这是使用64位浮点值时可以期望的最好结果。

What's probably happening is that the 32-bit build is using the 80-bit FPU registers to do the calculation and the 64-bit build is using the SIMD operations using 64-bit values, causing a slight discrepancy. Note that both answers agree to 14 decimal places, which is about the best you can hope for with 64-bit floating point values.

Visual C ++提供了编译器选项,可让您说出您是否更喜欢速度,一致性,浮点运算的精度。使用这些选项(例如 / fp:strict ),如果这对您很重要,则可能会在两个版本之间获得一致的值。

Visual C++ offers compiler options that let you say whether you prefer speed, consistency, or precision with regard to floating point operations. Using those options (e.g., /fp:strict), you can probably get consistent values between the two builds if that's important to you.

还请注意,VC ++ 2008相当老。较新的版本已修复了许多错误,包括与浮点相关的一些错误。 (自2008年以来,在开源软件中 strtod 的常见实现已检测到并修复了一些错误。)除了80位和64位操作之间的精度差异外,您还可以也遇到解析和显示错误。但是,浮点很难,并且错误仍然存​​在

Also note that VC++2008 is rather old. Newer versions have fixes for many bugs, including some related to floating point. (Popular implementations of strtod in open source software have had bugs detected and fixed since 2008.) In addition to the precision difference between 80-bit and 64-bit operations, you may also be encountering parsing and display bugs. Nonetheless, floating point is hard, and bugs persist.

这篇关于std :: pow在32位和64位应用程序中产生不同的结果的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆