round函数返回错误的双估计

use*_*434 2 c++ precision double

我试图将双倍加倍到3小数点,但......

double round_double(double d){
    return round(d * 1000) / 1000;
}

int main() {
    double r = round_double(1.5 * 1.001);
    cout << r << endl;
    return 0; }
Run Code Online (Sandbox Code Playgroud)

当我运行它时结果是1.501 ...为什么不返回1.502?当我将round_double函数更改为如下所示时:

return floor(d * 1000 + 0.5) / 1000;
Run Code Online (Sandbox Code Playgroud)

它仍然产生1.501 ...任何想法为什么?

Sta*_*tas 6

因为1.5 * 1.001没有确切的表示double.它被视为1.5014999999999998.

解决此问题的一种非常常见的方法是添加(减去)一些epsilon值.

使用epsilon校正的舍入函数可能看起来像

double round_double(double d)
{
    const double epsilon = 10e-8;
    d = signbit(d) ? d - epsilon : d + epsilon;
    return round(d * 1000) / 1000;
}
Run Code Online (Sandbox Code Playgroud)