On Nov 14, 2007, at 1:35 PM, Andy Dougherty wrote:
I'm forwarding a message I got about the f == 0.0 warnings.
--
Andy Dougherty [EMAIL PROTECTED]
---------- Forwarded message ----------
Date: Wed, 14 Nov 2007 10:38:10 -0500
From: Jeffrey Kegler <[EMAIL PROTECTED]>
To: Andy Dougherty <[EMAIL PROTECTED]>
Subject: Could you forward this into the perl6 internals list
Resent-Date: Wed, 14 Nov 2007 10:38:35 -0500
Resent-From: <[EMAIL PROTECTED]>
I've been following the floating point issue for some time, but am
not on the perl6 internals list, and didn't want to join to make a
single comment. Could I ask you to forward this into the list?
Bottom line: the floating point equality warning is the expression of
a philosophy of math issue, and you may not be following the
philosophy. That's cool. But it's not viable IMHO to not adhere to
the philosophy, but try to keep the warning.
The philosophy of math issue is that if you are taking floats as
approximations of reals, equality does not usually mean anything
useful. It almost never means what the programmer is trying to
express via equality. Floating point zero (0.00) means zero plus or
minus an error, just as with any other floating point number. Zero
is not special in any sense. Are all your "special case" floating
zeroes safe from being mistaken for certain very small but non-zero
numbers in all implementations?
The issue here is, the main places we test for equality of floats is in
an opcode(where the compiler can handle the approximation), or treating
cases of -0.0 and 0.0 causing different results with standard
libraries. Many of the equality checks are in fact explicitly checking
for equality with 0.0(and consequently -0.0) because different
libraries seem to have different handling for the two, intentionally or
not. Most of parrot is sort of akin to kernel mode programming, don't
use floats and find another way if you need floats.
However, we are hackers, not philosophers of mathematics (actually
I'm both, but I'm talking now as a hacker). Floats on computers are
what we hackers use them for, and if we find it useful to special
case the bit pattern corresponding to zero, we can do it. We should,
however, turn off the warning.
We can't use a bit pattern for all systems because that would require
knowing the underlying size of a float, it's bit layout, and being sure
that c can convert to and from it exactly(I don't believe c can nicely
handle an 80 bit float). The issue isn't so much 0.0 but -0.0, which
would have a different bit pattern and you lack guarantees about it,
there are none! I've never heard of a portable float, and as a result,
we can't assume anything. For the IEEE, -0.0 == 0.0 even though their
bit patterns are different. In complex.pmc, all tests pass on
ppc(darwin), i386(freebsd, plus smoke results seem ok), and
amd64(freebsd, plus linux smokes), but if you remove one of the
equality checks, one or more tests might fail, somewhere. Writing code
like "if (i == 0.0) i = 0.0;" looks like a no-op, but you're also
testing for -0.0 to handle libm issues. I'm not 100% sure how
compilers handle -0.0 in source on systems that don't support -0.0
floats.
I hesitated to come in, because I'm not aware of the context. You
may, for example, be trying to mix code that carefully adheres to the
floating-point-equals-Platonic-idea-of-real-numbers philosophy, with
code written on a it-works-so-what's-the-beef philosophy, in which
case I can see why the problem keeps coming up.
I think most of parrot's use of floats is "higher programs will want
them, so we need to provide them." If it weren't for want, there
wouldn't be a pdd15.
Primary suggestion: You might consider simply turning off the
warning in preference to heroic efforts to shut it up for cases which
are actually no safer than any others.
Other suggestions: If code rewrites are feasible, an additional
boolean is not (certainly in the context of C code) all that
expensive these days, and is a philosophically "right" answer. A
more hackerly solution is to identify a range which won't be the
result of normal computation and test for that. (If the value can
never be less than zero let (f < 0.00) be the special case.
Sorry to interrupt your work, but I've followed your list and seen
this come up several times and I hoped this might help,
thanks for your work,
jeffrey kegler