[Tim Peters']
[Steven D'Aprano]
It isn't necessary to look at complex numbers to see the difference
between positive and negative zero. Just look at a graph of y=1/x. In
particular, look at the behaviour of the graph around x=0. Now tell me
that the sign of zero doesn't make a difference.
OK, I looked, and it made no difference to me. Really. If I had an
infinitely tall monitor, maybe I could see a difference, but I don't
-- the sign of 0 on the nose makes no difference to the behavior of
1/x for any x other than 0. On my finite monitor, I see it looks like
the line x=0 is an asymptote, and the graph approaches minus infinity
on that line from the left and positive infinity from the right; the
value of 1/0 doesn't matter to that.
Signed zeroes also preserve 1/(1/x) == x for all x,
No, signed zeros "preverse" that identity for exactly the set {+Inf,
-Inf}, and that's all. That's worth something, but 1/(1/x) == x isn't
generally true in 754 anyway. Most obviously, when x is subnormal,
1/x overflows to an infinity (the 754 exponent range isn't symmetric
around 0 -- subnormals make it "heavy" on the negative side), and then
1/(1/x) is a zero, not x. 1/(1/x) == x doesn't hold for a great many
normal x either (pick a pile at random and check -- you'll find
counterexamples quickly).
admittedly at the cost of y==x iff 1/y == 1/x (which fails for y=-0 and x=+0).
Technically, -0 and +0 are not the same (for some definition of "technically"); but
practicality beats purity and it is more useful to have -0==+0 than the alternative.
Can just repeat that the only good rationale I've seen is in Kahan's
paper (previously referenced).
That's an implementation failure. Mathematically, the sign of 0**n should
depend only on whether n is odd or even. If c**n is ambiguous, then that's
a bug in the implementation, not the standard.
As I said, these are complex zeroes, not real zeroes. The 754
standard doesn't say anything about complex numbers. In rectangular
form, a complex zero contains two real zeroes. There are 4
possiblities for a complex zero if the components are 754
floats/doubles:
+0+0i
+0-0i
-0+0i
-0-0i
Implement Cartesian complex multiplication in the obvious way:
(a+bi)(c+di) = (ac-bd) + (ad+bc)i
Now use that to raise the four complex zeroes above to various integer
powers, trying different ways of grouping the multiplications. For
example, x**4 can be computed as
((xx)x)x
or
(xx)(xx)
or
x((xx)x)
etc. You'll discover that, in some cases, for fixed x and n, the
signs of the zeroes in the result depend how the multiplications were
grouped. The 754 standard says nothing about any of this, _except_
for the results of multiplying and adding 754 zeroes. Multiplication
of signed zeroes in 754 is associative. The problem is that the
extension to Cartesian complex multiplication isn't associative under
these rules in some all-zero cases, mostly because the sum of two
signed zeroes is (under 3 of the rounding modes) +0 unless both
addends are -0. Try examples and you'll discover this for yourself.
I was part of NCEG (the Numerical C Extension Group) at the time I
stumbled into this, and they didn't have any trouble following it
<wink>. It was a surprise to everyone at the time that Cartesian
multiplication of complex zeroes lost associativity when applying 754
rules in the obvious way, and no resolution was reached at that time.
Sounds to me that the Feds wanted something broken and you gave them
something that was working. No wonder they failed you
Yup, and they did a lot of that <0.9 wink>. Luckily(?), Fortran is so
eager to allow optimizations that failure due to numeric differences
in conformance tests rarely withstood challenge.