在Java划分后,大十进制值的总和应相等

  • 本文关键字:十进制 划分 Java java
  • 更新时间 :
  • 英文 :


我有6个 BigDecimals,可以说

a,b,c,d,e,f and tot所有这些值的总和(a,b,c,d,e,f)等于tot我正在计算平均值并存储在其他类型BigDecimal类型的变量中,只需说avgA, avgB, avgC, avgD, avgE, avgF and avgTot即可。现在,如果我添加所有这些

avgA, avgB, avgC, avgD, avgE, avgF 

此总和应等于avgTot

但所有平均值的总和(avgA, avgB, avgC, avgD, avgE, avgF)不等于totAvg

这是示例代码

BigDecimal avgA = a.divide(new BigDecimal(counter), 15,RoundingMode.CEILING);
BigDecimal avgB = b.divide(new BigDecimal(counter), 15,RoundingMode.CEILING);
BigDecimal avgTot = tot.divide(new BigDecimal(counter), 15,RoundingMode.CEILING);
BigDecimal trimA = avgA.setScale(4, RoundingMode.CEILING);
BigDecimal trimB = avgB.setScale(4, RoundingMode.CEILING);
BigDecimal trimTot = avgTot.setScale(4, RoundingMode.CEILING);

样本值: -

trimA 0.0004
trimB 0.0000
trimC 0.0022
trimD 0.0047
trimE 0.0000
trimF 0.0002
trimTot 0.0076

问题是sum(TrimA..F)不等于trimTot。我必须确保sum(TrimA..F)应等于trimTot

devious的事情是RoundingMode.CEILING可确保加法上的最大错误,而不是RoundingMode.HALF_UP

天花板

0.00031 => 0.0004
0.00211 => 0.0022
-------    ------ +
0.00242    0.0026

half_up(标准)

0.00033 => 0.0003
0.00216 => 0.0022
-------    ------ +
0.00249    0.0025

地板

0.00043 => 0.0004
0.00216 => 0.0021
-------    ------ +
0.00259    0.0025

so

BigDecimal trimA = avgA.setScale(4, RoundingMode.HALF_UP);
BigDecimal trimB = avgB.setScale(4, RoundingMode.HALF_UP);
BigDecimal trimTot = avgTot.setScale(4, RoundingMode.HALF_UP);

会最大程度地减少舍入错误,但不一定总是将其删除。

那么,您认为没有四舍五入到第四个小数。从15个职位到4时。

对于任何圆形方法来说,这根本不是这种情况,即一般圆(a b)= round(a) round(b)。

人们以高度精确地处理这些问题,以最大程度地减少可见的舍入错误的发生率,但这常常无法完全起作用。注意:Joop Eggen刚刚发布了这样的答案。请注意,我没有从判断力的意义上使用" Bodge"!

不提供为什么需要不可能的约束的解释,很难提供有用的建议。

一种明显的方法是定义 a,b,c为a/3 b/3 c/3的平均值。另一种方法是通过计算为理性数字来工作。这意味着要跟踪分子和分母或使用专门的Rational class

最新更新