I honestly do not know what's going on. Of course the float thing is obvious, but I fail to see why reordering the equation like this should change things. I've experimented using a slightly simplified version of the equation, changing values and moving things around.
eq.1 and eq.2 are the same as the OPs, eq.3 is equivalent to eq.1 thanks to operator preference (see ?Syntax
). *
and /
are evaluated before +
and -
, other than that they are evaluated from left to right, and parenthesis are resolved from inner to outer. So in eq.1 and eq.3 the order is -
/
*
+
, in eq.2 the order is -
*
/
+
.
a <- 100
b <- 100
c <- 0.1
e <- 0.3
r1 <- a / b * (e - c) + c # [1]
r2 <- (e - c) * a / b + c # [2]
r3 <- (e - c) * (a / b) + c # [3]
r1 == r2 # FALSE
r1 == r3 # TRUE
sprintf("%.20f", c(r1, r2, r3))
# "0.29999999999999998890" "0.30000000000000004441" "0.29999999999999998890"
It's clear that the exact value depends on the order of operations, although in purely arithmetic terms it shouldn't matter (they're associative). But the ordering only makes a difference when you're using some specific values. If you set a
and b
to 10 say, or set c
to 0.2, the values are identical. My hunch is that this is caused by division being done in integer mode in eq.1, and float mode in eq.2, the second introducing rounding errors the first one doesn't (contingent on starting values). The real take-home message is of course what markus linked to, you need to take extra care when comparing floats, but it would still be nice to have a definite explanation of this precise behaviour.