我正在编写一个我需要处理mm和英寸的应用程序。我已经编写了一些简单的代码来缩放两个度量单位,我也有一些代码来取一个十进制数并将其转换为分数。但是,当我使用Math.Floor从小数中分割整数时,我发现我并不总是得到返回的预期值。我附上了一些代码来证明问题。我希望最终的结果是6但我得到5.我很难理解为什么。有什么想法吗?
// This is a .Net 4.5 console application.
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
double ValA = 6;
double ValB = 0;
double ValC = 0;
double ValD = 0;
ValB = ValA * 25.4;
ValC = ValB / 25.4;
ValD = Math.Floor(ValC);
Console.WriteLine(ValA.ToString());
Console.WriteLine(ValB.ToString());
Console.WriteLine(ValC.ToString()); // This returns 6 as expected
Console.WriteLine(ValD.ToString()); // But this returns 5.
Console.ReadKey();
}
}
}
答案 0 :(得分:6)
双打不是十进制数的精确表示,它们用二进制数表示。它们不会精确转换为十进制数,因此您无法保证5 * 2.52 / 2.52等于5.0。我建议改用C#type Decimal。
有关C#Decimal类型
的更多信息,请参阅this question答案 1 :(得分:2)
此行的打印输出
Console.WriteLine(ValC.ToString());
有误导性:I / O库打印6,即使实际值略小于6:
Console.WriteLine(ValC < 6.0);
上面的行打印True
,这是有道理的:在乘以并除以相同数字之后累积的微小误差会妨碍。
根据IEEE-754计算器,25.4表示为25.399999618530273。在乘法和除法之后,有一个微小的差异相当于大约8E-16
,但是你得到的值略小于6.这就是Floor
正确返回5的原因。