C++ sqrt函数精度为正方形

Raf*_*mal 7 c++ floating-point-precision

设,x是一个整数和y = x * x.

那保证sqrt(y) == x吗?

例如,我可以确定sqrt(25)sqrt(25.0)将返回5.0,不是5.00000000034.999999998

Sir*_*Guy 8

符合IEEE-754标准的基本操作允许错误的实现(sqrt例如)需要正确舍入值.
这意味着误差将小于1/2 ULP(最后一个单位)或基本上尽可能接近实际答案.

要回答你的问题,如果实际答案完全由a表示,double那么你将得到确切的答案.

注意:这不是由C++标准保证,而是由IEEE-754标准保证,这对大多数人来说可能不是问题.

最终,一个简单的测试应该足以满足您的目的:

    for(int i = 0; i < (int)std::sqrt(std::numeric_limits<int>::max()); i++)
    {
        assert((int)(double)i == i);//Ensure exactly representable, because why not
        assert(std::sqrt((double)i*i) == i);
    }
Run Code Online (Sandbox Code Playgroud)

如果这个过去了,我认为没有理由担心.


Joe*_*e Z 5

不,您不能保证。对于适合浮点类型尾数动态范围的整数及其平方(典型的C / C ++ double值为2 ^ 53 ),您可能会没事,但不一定可以保证。

您应避免在浮点值和精确值(尤其是精确整数值)之间进行等值比较。浮点舍入模式和其他类似的东西确实会给您带来麻烦。

您要么想要使用“比较范围”来接受“近似相等”的结果,要么要使用整数来重铸算法。有多个StackOverflow问题涉及浮点相等比较。我建议您搜索并阅读。

对于某类问题,我在这里写了一个替代解决方案: 在一个间隔内找到所有数字的第n个根

该解决方案采用了不同于依赖棘手浮点算法的方法。