types. Update the regression tests and the documentation to reflect
this. Remove the UNSAFE_FLOATS #ifdef.
This is only half the story: we still unconditionally reject
floating point operations that result in +/- infinity. See
recent thread on -hackers for more information.
index 5f82a7848512047544941bb0b79662cce4a77299..c6093b846377f5babb6e6d965e9d82ab054c8490 100644 (file)
<!--
-$PostgreSQL: pgsql/doc/src/sgml/syntax.sgml,v 1.89 2003年11月29日 19:51:37 pgsql Exp $
+$PostgreSQL: pgsql/doc/src/sgml/syntax.sgml,v 1.90 2004年03月12日 00:25:40 neilc Exp $
-->
<chapter id="sql-syntax">
</literallayout>
</para>
+ <para>
+ In addition, there are several special constant values that are
+ accepted as numeric constants. The <type>float4</type> and
+ <type>float8</type> types allow the following special constants:
+<literallayout>
+Infinity
+-Infinity
+NaN
+</literallayout>
+ These represent the IEEE 754 special values
+ <quote>infinity</quote>, <quote>negative infinity</quote>, and
+ <quote>not-a-number</quote>, respectively. The
+ <type>numeric</type> type only allows <literal>NaN</>, whereas
+ the integral types do not allow any of these constants. Note that
+ these constants are recognized in a case-insensitive manner.
+ </para>
+
<para>
<indexterm><primary>integer</primary></indexterm>
<indexterm><primary>bigint</primary></indexterm>
index 2707c83fd62a43c487bdd7ba5a18943059d78437..aed643d862b858bf1d63c1255a73f3e8a186fbbd 100644 (file)
*
*
* IDENTIFICATION
- * $PostgreSQL: pgsql/src/backend/utils/adt/float.c,v 1.98 2004年03月11日 02:11:13 neilc Exp $
+ * $PostgreSQL: pgsql/src/backend/utils/adt/float.c,v 1.99 2004年03月12日 00:25:40 neilc Exp $
*
*-------------------------------------------------------------------------
*/
@@ -114,21 +114,14 @@ static int float8_cmp_internal(float8 a, float8 b);
/*
- * check to see if a float4 val is outside of
- * the FLOAT4_MIN, FLOAT4_MAX bounds.
+ * check to see if a float4 val is outside of the FLOAT4_MIN,
+ * FLOAT4_MAX bounds.
*
- * raise an ereport warning if it is
-*/
+ * raise an ereport() error if it is
+*/
static void
CheckFloat4Val(double val)
{
- /*
- * defining unsafe floats's will make float4 and float8 ops faster at
- * the cost of safety, of course!
- */
-#ifdef UNSAFE_FLOATS
- return;
-#else
if (fabs(val) > FLOAT4_MAX)
ereport(ERROR,
(errcode(ERRCODE_NUMERIC_VALUE_OUT_OF_RANGE),
ereport(ERROR,
(errcode(ERRCODE_NUMERIC_VALUE_OUT_OF_RANGE),
errmsg("type \"real\" value out of range: underflow")));
-
- return;
-#endif /* UNSAFE_FLOATS */
}
/*
- * check to see if a float8 val is outside of
- * the FLOAT8_MIN, FLOAT8_MAX bounds.
+ * check to see if a float8 val is outside of the FLOAT8_MIN,
+ * FLOAT8_MAX bounds.
*
- * raise an ereport error if it is
+ * raise an ereport() error if it is
*/
static void
CheckFloat8Val(double val)
{
- /*
- * defining unsafe floats's will make float4 and float8 ops faster at
- * the cost of safety, of course!
- */
-#ifdef UNSAFE_FLOATS
- return;
-#else
if (fabs(val) > FLOAT8_MAX)
ereport(ERROR,
(errcode(ERRCODE_NUMERIC_VALUE_OUT_OF_RANGE),
ereport(ERROR,
(errcode(ERRCODE_NUMERIC_VALUE_OUT_OF_RANGE),
errmsg("type \"double precision\" value out of range: underflow")));
-#endif /* UNSAFE_FLOATS */
}
/*
* empty strings, but emit a warning noting that the feature
* is deprecated. In 7.6+, the warning should be replaced by
* an error.
- *
- * XXX we should accept "Infinity" and "-Infinity" too, but
- * what are the correct values to assign? HUGE_VAL will
- * provoke an error from CheckFloat4Val.
*/
if (*num == '0円')
{
}
else if (strcasecmp(num, "NaN") == 0)
val = NAN;
+ else if (strcasecmp(num, "Infinity") == 0)
+ val = HUGE_VAL;
+ else if (strcasecmp(num, "-Infinity") == 0)
+ val = -HUGE_VAL;
else
ereport(ERROR,
(errcode(ERRCODE_INVALID_TEXT_REPRESENTATION),
* if we get here, we have a legal double, still need to check to see
* if it's a legal float
*/
- CheckFloat4Val(val);
+ if (!isinf(val))
+ CheckFloat4Val(val);
PG_RETURN_FLOAT4((float4) val);
}
errmsg("invalid input syntax for type double precision: \"%s\"",
num)));
- CheckFloat8Val(val);
+ if (!isinf(val))
+ CheckFloat8Val(val);
PG_RETURN_FLOAT8(val);
}
index 8226c6d5cf72114d6f80e0106fd3eb7a83e428d0..6fcf38ec7b1cc44d5f18a65ecb1b6758cc96d5ec 100644 (file)
* for developers. If you edit any of these, be sure to do a *full*
* rebuild (and an initdb if noted).
*
- * $PostgreSQL: pgsql/src/include/pg_config_manual.h,v 1.10 2004年02月11日 22:55:26 tgl Exp $
+ * $PostgreSQL: pgsql/src/include/pg_config_manual.h,v 1.11 2004年03月12日 00:25:40 neilc Exp $
*------------------------------------------------------------------------
*/
*/
#define DEFAULT_PGSOCKET_DIR "/tmp"
-/*
- * Defining this will make float4 and float8 operations faster by
- * suppressing overflow/underflow checks.
- */
-/* #define UNSAFE_FLOATS */
-
/*
* The random() function is expected to yield values between 0 and
* MAX_RANDOM_VALUE. Currently, all known implementations yield
index 124b7c378c69fdf78c0c0fd7ea601a4412bd6a3c..e4d460359fefd6150e7c8441f27b048d88dd4aee 100644 (file)
NaN
(1 row)
+SELECT 'infinity'::float4;
+ float4
+----------
+ Infinity
+(1 row)
+
+SELECT ' -INFINiTY '::float4;
+ float4
+-----------
+ -Infinity
+(1 row)
+
-- bad special inputs
SELECT 'N A N'::float4;
ERROR: invalid input syntax for type real: "N A N"
+SELECT 'NaN x'::float4;
+ERROR: invalid input syntax for type real: "NaN x"
+SELECT ' INFINITY x'::float4;
+ERROR: invalid input syntax for type real: " INFINITY x"
+SELECT 'Infinity'::float4 + 100.0;
+ERROR: type "double precision" value out of range: overflow
+SELECT 'Infinity'::float4 / 'Infinity'::float4;
+ ?column?
+----------
+ NaN
+(1 row)
+
+SELECT 'nan'::float4 / 'nan'::float4;
+ ?column?
+----------
+ NaN
+(1 row)
+
SELECT '' AS five, FLOAT4_TBL.*;
five | f1
------+-------------
index 89e2bbf90256977c90487c92669a29d9f476ee81..798a67c04fe4fc4ef2909aecd1799d3c9346931b 100644 (file)
NaN
(1 row)
+SELECT 'infinity'::float8;
+ float8
+----------
+ Infinity
+(1 row)
+
+SELECT ' -INFINiTY '::float8;
+ float8
+-----------
+ -Infinity
+(1 row)
+
-- bad special inputs
SELECT 'N A N'::float8;
ERROR: invalid input syntax for type double precision: "N A N"
+SELECT 'NaN x'::float8;
+ERROR: invalid input syntax for type double precision: "NaN x"
+SELECT ' INFINITY x'::float8;
+ERROR: invalid input syntax for type double precision: " INFINITY x"
+SELECT 'Infinity'::float8 + 100.0;
+ERROR: type "double precision" value out of range: overflow
+SELECT 'Infinity'::float8 / 'Infinity'::float8;
+ ?column?
+----------
+ NaN
+(1 row)
+
+SELECT 'nan'::float8 / 'nan'::float8;
+ ?column?
+----------
+ NaN
+(1 row)
+
SELECT '' AS five, FLOAT8_TBL.*;
five | f1
------+----------------------
index b7b64f2e50ea835730442634864beed4ed0064c3..a7147409ec98c6ab72fd885b82401b79311933a7 100644 (file)
@@ -29,8 +29,17 @@ INSERT INTO FLOAT4_TBL(f1) VALUES ('123 5');
SELECT 'NaN'::float4;
SELECT 'nan'::float4;
SELECT ' NAN '::float4;
+SELECT 'infinity'::float4;
+SELECT ' -INFINiTY '::float4;
-- bad special inputs
SELECT 'N A N'::float4;
+SELECT 'NaN x'::float4;
+SELECT ' INFINITY x'::float4;
+
+SELECT 'Infinity'::float4 + 100.0;
+SELECT 'Infinity'::float4 / 'Infinity'::float4;
+SELECT 'nan'::float4 / 'nan'::float4;
+
SELECT '' AS five, FLOAT4_TBL.*;
index 1e5e8ad4302278b66f7c0ae4c3332e79bee61c0d..593df68a326d9e3ba35486d2eac983d3b3fab837 100644 (file)
@@ -29,8 +29,16 @@ INSERT INTO FLOAT8_TBL(f1) VALUES ('123 5');
SELECT 'NaN'::float8;
SELECT 'nan'::float8;
SELECT ' NAN '::float8;
+SELECT 'infinity'::float8;
+SELECT ' -INFINiTY '::float8;
-- bad special inputs
SELECT 'N A N'::float8;
+SELECT 'NaN x'::float8;
+SELECT ' INFINITY x'::float8;
+
+SELECT 'Infinity'::float8 + 100.0;
+SELECT 'Infinity'::float8 / 'Infinity'::float8;
+SELECT 'nan'::float8 / 'nan'::float8;
SELECT '' AS five, FLOAT8_TBL.*;