美文网首页
【C#】浮点数精度避坑

【C#】浮点数精度避坑

作者: 冰麟轻武 | 来源:发表于2022-10-09 21:37 被阅读0次

1. 问题描述

关于数字精度问题,很多同学都肯定不陌生了,最经典的就是JS中的0.1+0.2


01+0.2 != 0.3

2. 具体表现

C#中也存在同样数字精度问题。

例如:
float的精度只能保存7位有效数字(参考C#中float的取值范围和精度分析
下面这段代码将得到1.01

float number = float.Parse("1.0099999");
Console.WriteLine(number.ToString());  // 1.01

同样的问题double也存在

如果说上面2个情况平时不容易碰到的话,可以看看下面的例子

0.015四舍五入得到0.01

同样的代码,类型换成doubledecimal就没有问题了

原因是Math.Round无法传入float类型的参数,float会隐式转换成double,但是在转换过程中会丢失精度

(double)0.015F; //0.01499999...

3. 关于四舍五入

Math.Round的默认行为并不是四舍五入

官方文档描述为:舍入到最接近的数字的策略,当数字在两个数字之间的中间时,它将舍入到最接近的偶数。

具体可参考:枚举 System.MidpointRounding.ToEven

具体表现是:


如果要使用我们常规理解上的四舍五入,需要使用参数 MidpointRounding.AwayFromZero

4. 建议

  1. 实际编码中尽量使用 decimal,避免使用float
  2. floatdoublefloatdecimaldoubledecimal,使用字符串作为中介,尽可能的保留精度;
    如:double.Parse(float.ToString("g9"))

    "g17"(double) 或"g9"(float)能尽可能的保留精度,详见标准数字格式字符串“G”或“g”小结

  3. 以上部分缺陷在.net5后续版本的.NET中有所改善。

相关文章

  • 【C#】浮点数精度避坑

    1. 问题描述 关于数字精度问题,很多同学都肯定不陌生了,最经典的就是JS中的0.1+0.2 2. 具体表现 C#...

  • iOS浮点数精度问题

    前言 浮点数是无法精确表示大部分实数的 单精度浮点数和双精度浮点数 单精度(float),一般在计算机中存储占用4...

  • 浮点数

    双精度浮点数类型 double单精度浮点数类型 float 以上两种都使用 浮点数 来表示小数 : 与之相对的是 ...

  • mysql8 数据类型 float double decimal

    float数值类型用于表示单精度浮点数值,而double数值类型用于表示双精度浮点数值,float和double都...

  • JavaScript浮点数的精度问题深究

    JavaScript浮点数的精度问题 javascript浮点数的精度问题是老生常谈了,但往往只知道0.1 + 0...

  • py_28 Decimal处理小数计算精度问题

    python Decimal这个类处理浮点数精度 浮点数在内存中存储的时候因为存储机制的原因,天然存在精度丢失的现...

  • sys库

    sys.float_info查询浮点数精度

  • C 浮点数

    浮点数存储带来的问题 问题背景 计算机中浮点数(float或double类型)都有精度范围,对于超出精度范围的浮点...

  • swift4-浮点类型

    //定义一个浮点类型var a = 1.5//定义一个单精度浮点数,表示32位浮点数,对数据精度要求不高可以使用此...

  • 1.3 Float 浮点型

    浮点型,也叫浮点数float、双精度数double或实数real。 浮点数在精度上会存在一些误差,所以永远不要相信...

网友评论

      本文标题:【C#】浮点数精度避坑

      本文链接:https://www.haomeiwen.com/subject/bsdnartx.html