为什么将值解析为双精度类型返回的结果与将其解析为小数类型然后转换为双精度类型返回的结果不同?

本文关键字:类型 双精度 返回 结果 转换 然后 为什么 小数 | 更新日期: 2023-09-27 18:15:55

尝试从字符串中解析值-36.845167:

double result;
double.TryParse("-36.845167", out result);
结果

-36.845167000000004

decimal value;
decimal.TryParse("-36.845167", out value);
double result = (double)value;

result is -36.845167

为什么会这样?

为什么将值解析为双精度类型返回的结果与将其解析为小数类型然后转换为双精度类型返回的结果不同?

两个双括号-36.845167分别为-36.84516700000000355430529452860355377197265625和-36.84516699999999644887793692760169506072998046875

它们与精确值相差3.55112206307239830493927001953125E-15和分别为3.55430529452860355377197265625 e15汽油。

第一个非常接近,所以它是正确的IEEE 754四舍五入到最接近的结果。我不知道将c#小数转换为双精度的标准要求是什么,但是,假设您在两种情况下使用了相同的输出方法,它可能没有做到四舍五入。

这是因为double的精度有限,而decimal存储的是十进制数字。在这里阅读更多:在。net中,小数、浮点数和双精度的区别?

基本上,decimal更好地存储十进制表示的数字。

编辑:更明确地回答您的原始问题:您的两个结果都有点不正确,因为-36.845167不能表示为double。看看这个表达式的输出:

 result.ToString("G20")

,你会看到它们都不等于-36.845167:其中一个是-36.845166999999996,另一个是-36.845167000000004

所以,它们都是4e-15你原来的数字。在调试器中(或在输出到控制台时)真正看到的只是转换为字符串期间的舍入。