What could be the reason for difference in floating point accuracy here?
def "emi test"(){
given:
def P = 6000000.00
def n = 20 * 12
def r = (8.35/12)/100
double emi_g = (P * r * (1+r).power(n)) / ((1+r).power(n) - 1)
double emi_j= (P * r * Math.pow(1+r,n)) / (Math.pow(1+r,n)-1);
expect:
emi_g == emi_j
}
result:
emi_g == emi_j
| | |
| | 51501.177737160346
| false
51501.177737160666
The issue is related to types.
(1 + r).power(n) - 1
evaluates to a BigDecimal
P * r * (1 + r).power(n)
evaluates to a BigDecimal
P * r * Math.pow(1 + r, n)
evaluates to a Double
Math.pow(1 + r, n) - 1
evaluates to a Double
It isn't clear what your requirements are and whether or not you care about the precision being lost and knowing those requirements would help describe how to get the desired behavior. The answer to the question as asked...
What could be the reason for difference in floating point accuracy here?
Is because the expressions evaluate to different types and the rules associated with dividing a Double
by a Double
(and the fact that you are the numerator and denominator values are in a Double
to begin with, as opposed to BigDecimial
) cause you to lose some precision.