[Python-ideas] Way to check for floating point "closeness"?

Chris Barker - NOAA Federal chris.barker at noaa.gov
Sun Jan 18 05:18:04 CET 2015


> provides a "significant figures comparison" (whatever that means,

Poor choice of words on my part -- that is not a clearly defined term.
I meant relative difference comparison, which does, more or less,
indicate that two values are the same to within N significant figures.
If you set the relative tolerance to 1e-6 then the values are "close"
to about the first 6 decimal digits.

>> According to Neil Girdhar,
>> absolute(/a/ - /b/) <= (/atol/ + /rtol/ * absolute(/b/))
>> which I presume means, in Python,
>> abs(a-b) <= atol + rtol * abs(b)
>> where atol and rtol are assume >= 0.0
>
> Adding the error tolerances together is a dubious thing to do. I don't
> understand the reasoning between that.

It ends up making the absolute tolerance essentially the "minimum
tolerance". If the scaled relative tolerance is much larger than the
absolute tolerance, it makes no difference. Likewise the other way
around for small relative tolerance. It does change the result when
the two are about the same magnitude, but this is all an order of
magnitude thing anyway -- a factor of two doesn't really change the
result.

On a phone right now, but I guess that it was implemented that way to
make it easy to vectorize with numpy arrays. If checks are a pain to
vectorize.

I think it's an OK way to do it , but very bad idea for the absolute
tolerance to default to anything but zero.

And really, it makes more sense to specify either absolute or
relative, rather that mixing them.

The numpy approach goes to heck for values smaller than zero.
Essentially you need to know the scale to set the absolute tolerance
anyway, killing the point of a relative tolerance.
> I cannot think of a good justification for that. Either I am missing
> something,

See above

> or this goes to show that numpy can mess up even something as
> simple and straightforward as an error calculation.

I'm not going to say that it messed up--but I certainly don't think
that we should feel any obligation to do it the same way.

> If I'm right, that's
> further evidence that getting this "right" and putting it in the
> standard library is a good thing to do.

I do think this takes some thought, so good to put it in.

But this thread also makes it clear that there a lot of ways to define
"close", and which is best is use-case dependent. I think a
straightforward relative tolerance would be usefull enough in many
cases, and maybe an absolute one would be good for completeness.

But I can see the argument that if there isn't one available, then
folks are forced to think for themselves about what "closeness" means
in their case, and be les likely to simply use the one provided when
it might not be appropriate.

(I need to go back and check some of my tests, for instance, I'm sure
I didn't always think about the numpy abs_ tol parameter carefully!)

> I didn't think that the well-known difficulties in root-finding has
> anything to do with the usefulness of a standard way to compare numbers
> for approximate equality.

Agreed -- termination criteria of numerical methods is not the use
case for a generic is_close implementation. That clearly requires a
use-case specific criteria.


More information about the Python-ideas mailing list