Thread: Re: [BUGS] BUG #4660: float functions return -0

Re: [BUGS] BUG #4660: float functions return -0

From
ITAGAKI Takahiro
Date:
I reported the following bug to -bugs, and I'd like to discuss
whether we need to fix the issue or how to fix it.

"ITAGAKI Takahiro" <itagaki.takahiro@oss.ntt.co.jp> wrote:
> Bug reference:      4660
> PostgreSQL version: 8.3.3
> Operating system:   Fedora 8
> Description:        float functions return -0
> Details: 
> Float8 versions of trunc(), ceil() and round() could return -0 on some
> version of glibc.
> 
> postgres=# SELECT pg_catalog.trunc((-0.1)::float8);
>     -0
> postgres=# SELECT pg_catalog.ceil((-0.1)::float8);
>    -0
> postgres=# SELECT pg_catalog.round((-0.1)::float8);
>     -0

We already have some codes to avoid -0 float8um (unary minus),
but there are no protection in trunc(), ceil() and round() at least.
It is platform-dependent behavior (msvcrt doesn't return -0), and there is
a difference between float8 and numeric (numeric doesn't support -0).
 1. Remove 'avoid -0' from float8um because -0 is a possible value    for floating point numbers. 2. Add 'avoid -0'
codesto those functions.    (Are there any places where we also add it?) 3. Move 'avoid -0' codes to float8out() and
float8send().   '-0' could be stored in database, but users receives only '+0'.
 

Fixes might be needed by float4 versions.
I'll write a patch when we come to a decision.

Regards,
---
ITAGAKI Takahiro
NTT Open Source Software Center




Re: [BUGS] BUG #4660: float functions return -0

From
Tom Lane
Date:
ITAGAKI Takahiro <itagaki.takahiro@oss.ntt.co.jp> writes:
> We already have some codes to avoid -0 float8um (unary minus),
> but there are no protection in trunc(), ceil() and round() at least.

I looked into the CVS history to find out when the anti-minus-zero code
got put into float8um.  It seems to have been done by Tom Lockhart here:

http://anoncvs.postgresql.org/cvsweb.cgi/pgsql/src/backend/utils/adt/float.c.diff?r1=1.13;r2=1.14

The CVS commit message saysCheck for zero in unary minus floating point code (IEEE allows anexplicit negative zero
whichlooks ugly in a query result!).
 
along with some other unrelated changes.  I can find no evidence in the
mailing list archives that there was any discussion about the point,
so I think Tom did that on his own authority.

I'm of the opinion that minus zero was put into the IEEE floating point
standard by people who know a great deal more about the topic than
anyone on this list does, and that we do not have the expertise to be
second-guessing how it should work.  Not long ago we took out code that
was interfering with spec-compliant treatment of IEEE infinity; I think
we should take out this code too.

Yes, it will be platform dependent, because various platforms get the
IEEE spec wrong to some degree, but so what?  This is hardly the only
platform dependence of that kind.
        regards, tom lane


Re: [BUGS] BUG #4660: float functions return -0

From
Bruce Momjian
Date:
Tom Lane wrote:
> ITAGAKI Takahiro <itagaki.takahiro@oss.ntt.co.jp> writes:
> > We already have some codes to avoid -0 float8um (unary minus),
> > but there are no protection in trunc(), ceil() and round() at least.
> 
> I looked into the CVS history to find out when the anti-minus-zero code
> got put into float8um.  It seems to have been done by Tom Lockhart here:
> 
> http://anoncvs.postgresql.org/cvsweb.cgi/pgsql/src/backend/utils/adt/float.c.diff?r1=1.13;r2=1.14
> 
> The CVS commit message says
>     Check for zero in unary minus floating point code (IEEE allows an
>     explicit negative zero which looks ugly in a query result!).
> along with some other unrelated changes.  I can find no evidence in the
> mailing list archives that there was any discussion about the point,
> so I think Tom did that on his own authority.
> 
> I'm of the opinion that minus zero was put into the IEEE floating point
> standard by people who know a great deal more about the topic than
> anyone on this list does, and that we do not have the expertise to be
> second-guessing how it should work.  Not long ago we took out code that
> was interfering with spec-compliant treatment of IEEE infinity; I think
> we should take out this code too.
> 
> Yes, it will be platform dependent, because various platforms get the
> IEEE spec wrong to some degree, but so what?  This is hardly the only
> platform dependence of that kind.

Agreed.

--  Bruce Momjian  <bruce@momjian.us>        http://momjian.us EnterpriseDB
http://enterprisedb.com
 + If your life is a hard drive, Christ can be your backup. +


Re: [BUGS] BUG #4660: float functions return -0

From
Gregory Stark
Date:
Tom Lane <tgl@sss.pgh.pa.us> writes:

> The CVS commit message says
>     Check for zero in unary minus floating point code (IEEE allows an
>     explicit negative zero which looks ugly in a query result!).

> I'm of the opinion that minus zero was put into the IEEE floating point
> standard by people who know a great deal more about the topic than
> anyone on this list does, and that we do not have the expertise to be
> second-guessing how it should work.  Not long ago we took out code that
> was interfering with spec-compliant treatment of IEEE infinity; I think
> we should take out this code too.

If the original complaint was that it looked ugly in query results then the
right way to fix it would surely in float4out and float8out. Interfering with
IEEE floating points may be a bad idea but surely it's up to us how we want to
represent those values in text.

But without a convenient and widely used binary format that kind of restricts
our options. If we squash -0 on float[48]out then dumps will lose information.
So I guess there's nothing we can do about it now. I wonder if we're going to
find users complaining about things like "displaying -0 matching results"
though...


--  Gregory Stark EnterpriseDB          http://www.enterprisedb.com Ask me about EnterpriseDB's Slony Replication
support!


Re: [BUGS] BUG #4660: float functions return -0

From
Tom Lane
Date:
Gregory Stark <stark@enterprisedb.com> writes:
> Tom Lane <tgl@sss.pgh.pa.us> writes:
>> I'm of the opinion that minus zero was put into the IEEE floating point
>> standard by people who know a great deal more about the topic than
>> anyone on this list does, and that we do not have the expertise to be
>> second-guessing how it should work.  Not long ago we took out code that
>> was interfering with spec-compliant treatment of IEEE infinity; I think
>> we should take out this code too.

> If the original complaint was that it looked ugly in query results then the
> right way to fix it would surely in float4out and float8out. Interfering with
> IEEE floating points may be a bad idea but surely it's up to us how we want to
> represent those values in text.

> But without a convenient and widely used binary format that kind of restricts
> our options. If we squash -0 on float[48]out then dumps will lose information.

The point I'm trying to make is that we should deliver IEEE-compliant
results if we are on a platform that complies with the spec.  Right down
to the minus sign.  If that surprises people who are unfamiliar with the
spec, well, there are a lot of things about floating point arithmetic
that surprise people who aren't familiar with it.
        regards, tom lane


Re: [BUGS] BUG #4660: float functions return -0

From
Brendan Jurd
Date:
On Wed, Feb 18, 2009 at 2:57 AM, Tom Lane <tgl@sss.pgh.pa.us> wrote:
> The point I'm trying to make is that we should deliver IEEE-compliant
> results if we are on a platform that complies with the spec.  Right down
> to the minus sign.  If that surprises people who are unfamiliar with the
> spec, well, there are a lot of things about floating point arithmetic
> that surprise people who aren't familiar with it.

Agreed.  There are plenty of things about floats that are downright
wonky, and when people start seeing minus zero in their float
computations it might prompt them into doing some reading, and
figuring out that what they really wanted was numeric.

(not saying that floats are without application, but I've often
encountered them in places they ought not to be)

Cheers,
BJ


Re: [BUGS] BUG #4660: float functions return -0

From
Tom Lane
Date:
Brendan Jurd <direvus@gmail.com> writes:
> On Wed, Feb 18, 2009 at 2:57 AM, Tom Lane <tgl@sss.pgh.pa.us> wrote:
>> The point I'm trying to make is that we should deliver IEEE-compliant
>> results if we are on a platform that complies with the spec.  Right down
>> to the minus sign.  If that surprises people who are unfamiliar with the
>> spec, well, there are a lot of things about floating point arithmetic
>> that surprise people who aren't familiar with it.

> Agreed.  There are plenty of things about floats that are downright
> wonky, and when people start seeing minus zero in their float
> computations it might prompt them into doing some reading, and
> figuring out that what they really wanted was numeric.

I pulled the special code out of float8um/float4um and got the following
two changes in the regression tests:

*** src/test/regress/expected/numerology.out    Mon Aug  4 22:43:18 2008
--- src/test/regress/results/numerology.out    Tue Feb 17 20:05:01 2009
***************
*** 92,98 ****   ORDER BY two, max_float, min_float;  two |      max_float       |       min_float
-----+----------------------+-----------------------
!    1 | 1.2345678901234e+200 |                     0    2 |                    0 | -1.2345678901234e+200 (2 rows) 
--- 92,98 ----   ORDER BY two, max_float, min_float;  two |      max_float       |       min_float
-----+----------------------+-----------------------
!    1 | 1.2345678901234e+200 |                    -0    2 |                    0 | -1.2345678901234e+200 (2 rows) 
***************
*** 104,110 ****   ORDER BY two, max_float, min_float;  two |      max_float       |       min_float
-----+----------------------+-----------------------
!    1 | 1.2345678901234e+200 |                     0    2 |                    0 | -1.2345678901234e+200 (2 rows) 
--- 104,110 ----   ORDER BY two, max_float, min_float;  two |      max_float       |       min_float
-----+----------------------+-----------------------
!    1 | 1.2345678901234e+200 |                    -0    2 |                    0 | -1.2345678901234e+200 (2 rows) 

======================================================================

This is on a minus-zero-clean platform of course (same results on Fedora
9 and current Mac OS X).  My HP box still produces the old results,
so we will need two variants of this expected-result file.  Other
platforms might show yet other diffs of course, but we'll have to wait
for buildfarm results to know more.

Last call for objections ...
        regards, tom lane