Math.Floor行为

时间:2013-01-30 21:26:54

标签: c# .net

double c, d, e;
double a = (c - d) / e;
double b = Math.Floor(a);
Debug.WriteLine(a.ToString() + " " + b.ToString());

上面的代码在一个配置中输出“3 2”,其中所有数字都是双倍的。这怎么可能?是因为双重操作导致的分数误差?但是我认为a.ToString()应该给出整数和它的小数部分。

1 个答案:

答案 0 :(得分:10)

这只是double.ToString()所做的事情。这是一个简短但完整的程序,展示了同样的事情:

using System;

public class Test
{
    static void Main(string[] args)
    {
        // Find the largest double less than 3
        long bits = BitConverter.DoubleToInt64Bits(3);
        double a = BitConverter.Int64BitsToDouble(bits - 1);
        double b = Math.Floor(a);
        // Print them using the default conversion to string...
        Console.WriteLine(a.ToString() + " " + b.ToString());
        // Now use round-trip formatting...
        Console.WriteLine(a.ToString("r") + " " + b.ToString("r"));
    }
}

输出:

3 2
2.9999999999999996 2

现在double.ToString()记录在:

  

此版本的ToString方法隐式使用当前文化的通用数字格式说明符(“G”)和NumberFormatInfo。

...和general numeric format specifier文档状态:

  

精度说明符定义可以在结果字符串中显示的最大有效位数。如果省略精度说明符或为零,则数字类型将确定默认精度,如下表所示。

...表格显示double的默认精度为15.如果您认为2.9999999999999996舍入为15位有效数字,则最终为3。

事实上,a完全值是:

2.999999999999999555910790149937383830547332763671875

...当被视为15位有效数字时再为3。