Floating point bug?
jeff at schwabcenter.com
Sat Feb 16 02:30:03 CET 2008
Steven D'Aprano wrote:
> On Fri, 15 Feb 2008 10:55:47 -0800, Zentrader wrote:
>> I disagree with this statement
>> <quote>But that doesn't change the fact that it will expose the same
>> rounding-errors as floats do - just for different numbers. </quote> The
>> example used has no rounding errors.
> Of course it does. Three thirds equals one, not 0.9999, or
> 0.9999999999999999999999999999, or any other finite decimal
> representation. That's a rounding error, regardless of whether you are
> rounding in base 2 (like floats) or in base 10 (like Decimal does).
>> Also you can compare two
>> decimal.Decimal() objects for equality. With floats you have to test
>> for a difference less than some small value.
> That's a superstition.
> As a heuristic, it is often wise to lower your expectations when testing
> for equality. Since you often don't know how much rounding error will be
> introduced into a calculation, demanding that a calculation has zero
> rounding error is often foolish.
> But good advice becomes a superstition when it becomes treated as a law:
> "never test floats for equality". That's simply not true. For example,
> floats are exact for whole numbers, up to the limits of overflow.
That's not true. Epsilon becomes large (in absolute terms) for large
numbers. For 64-bit IEEE floats, eps > 1 at about 10**16.
> If you
> know your floats are whole numbers, and still writing something like this:
> x = 1234.0
> y = 1000.0 + 200.0 + 30.0 + 4.0
> if abs(x-y) < 1e-12:
> print "x and y are equal"
> then you are wasting your time and guilty of superstitious behaviour.
In what way? It's true that you hard-coded integers for which the
margin of error happens to be < 1, but there's nothing magical about
whole numbers. If you need to test for exact equality, you still can
only check within the limits of the float's precision.
>>> 1e16 + 1 == 10000000000000000
>>> 1e16 == 10000000000000000 - 1
More information about the Python-list