Hello I was surprised so PostgreSQL doesn't support this basic output format.
Regards Pavel Stehule
*** ./src/backend/utils/adt/formatting.c.orig 2009-04-10 11:31:17.000000000 +0200 --- ./src/backend/utils/adt/formatting.c 2009-04-10 18:05:14.000000000 +0200 *************** *** 335,340 **** --- 335,341 ---- #define NUM_F_MULTI (1 << 11) #define NUM_F_PLUS_POST (1 << 12) #define NUM_F_MINUS_POST (1 << 13) + #define NUM_F_EEEE (1 << 14) #define NUM_LSIGN_PRE (-1) #define NUM_LSIGN_POST 1 *************** *** 355,360 **** --- 356,362 ---- #define IS_PLUS(_f) ((_f)->flag & NUM_F_PLUS) #define IS_ROMAN(_f) ((_f)->flag & NUM_F_ROMAN) #define IS_MULTI(_f) ((_f)->flag & NUM_F_MULTI) + #define IS_EEEE(_f) ((_f)->flag & NUM_F_EEEE) /* ---------- * Format picture cache *************** *** 821,827 **** {"B", 1, NUM_B}, /* B */ {"C", 1, NUM_C}, /* C */ {"D", 1, NUM_D}, /* D */ ! {"E", 1, NUM_E}, /* E */ {"FM", 2, NUM_FM}, /* F */ {"G", 1, NUM_G}, /* G */ {"L", 1, NUM_L}, /* L */ --- 823,829 ---- {"B", 1, NUM_B}, /* B */ {"C", 1, NUM_C}, /* C */ {"D", 1, NUM_D}, /* D */ ! {"EEEE", 4, NUM_E}, /* E */ {"FM", 2, NUM_FM}, /* F */ {"G", 1, NUM_G}, /* G */ {"L", 1, NUM_L}, /* L */ *************** *** 1043,1048 **** --- 1045,1058 ---- if (n->type != NODE_TYPE_ACTION) return; + + if (IS_EEEE(num) && n->key->id != NUM_E) + { + NUM_cache_remove(last_NUMCacheEntry); + ereport(ERROR, + (errcode(ERRCODE_SYNTAX_ERROR), + errmsg("cannot use \"EEEE\" and others"))); + } switch (n->key->id) { *************** *** 1217,1226 **** break; case NUM_E: ! NUM_cache_remove(last_NUMCacheEntry); ! ereport(ERROR, ! (errcode(ERRCODE_FEATURE_NOT_SUPPORTED), ! errmsg("\"E\" is not supported"))); } return; --- 1227,1249 ---- break; case NUM_E: ! if (IS_EEEE(num)) ! { ! NUM_cache_remove(last_NUMCacheEntry); ! ereport(ERROR, ! (errcode(ERRCODE_SYNTAX_ERROR), ! errmsg("cannot use \"EEEE\" twice"))); ! } ! if (IS_BLANK(num) || IS_FILLMODE(num) || IS_LSIGN(num) || IS_BRACKET(num) ! || IS_MINUS(num) || IS_PLUS(num) || IS_ROMAN(num) || IS_MULTI(num)) ! { ! NUM_cache_remove(last_NUMCacheEntry); ! ereport(ERROR, ! (errcode(ERRCODE_SYNTAX_ERROR), ! errmsg("cannot use \"EEEE\" and others"))); ! } ! num->flag |= NUM_F_EEEE; ! break; } return; *************** *** 4138,4143 **** --- 4161,4178 ---- --Np->Num->zero_start; /* + * Short code for EEEE format + */ + if (IS_EEEE(Np->Num)) + { + if (!Np->is_to_char) + ereport(ERROR, + (errcode(ERRCODE_FEATURE_NOT_SUPPORTED), + errmsg("\"EEEE\" not supported"))); + return strcpy(inout, number); + } + + /* * Roman correction */ if (IS_ROMAN(Np->Num)) *************** *** 4232,4238 **** #ifdef DEBUG_TO_FROM_CHAR elog(DEBUG_elog_output, ! "\n\tSIGN: '%c'\n\tNUM: '%s'\n\tPRE: %d\n\tPOST: %d\n\tNUM_COUNT: %d\n\tNUM_PRE: %d\n\tSIGN_WROTE: %s\n\tZERO: %s\n\tZERO_START: %d\n\tZERO_END: %d\n\tLAST_RELEVANT: %s\n\tBRACKET: %s\n\tPLUS: %s\n\tMINUS: %s\n\tFILLMODE: %s\n\tROMAN: %s", Np->sign, Np->number, Np->Num->pre, --- 4267,4273 ---- #ifdef DEBUG_TO_FROM_CHAR elog(DEBUG_elog_output, ! "\n\tSIGN: '%c'\n\tNUM: '%s'\n\tPRE: %d\n\tPOST: %d\n\tNUM_COUNT: %d\n\tNUM_PRE: %d\n\tSIGN_WROTE: %s\n\tZERO: %s\n\tZERO_START: %d\n\tZERO_END: %d\n\tLAST_RELEVANT: %s\n\tBRACKET: %s\n\tPLUS: %s\n\tMINUS: %s\n\tFILLMODE: %s\n\tROMAN: %s\n\tEEEE: %s", Np->sign, Np->number, Np->Num->pre, *************** *** 4248,4254 **** IS_PLUS(Np->Num) ? "Yes" : "No", IS_MINUS(Np->Num) ? "Yes" : "No", IS_FILLMODE(Np->Num) ? "Yes" : "No", ! IS_ROMAN(Np->Num) ? "Yes" : "No" ); #endif --- 4283,4290 ---- IS_PLUS(Np->Num) ? "Yes" : "No", IS_MINUS(Np->Num) ? "Yes" : "No", IS_FILLMODE(Np->Num) ? "Yes" : "No", ! IS_ROMAN(Np->Num) ? "Yes" : "No", ! IS_EEEE(Np->Num) ? "Yes" : "No" ); #endif *************** *** 4618,4623 **** --- 4654,4680 ---- int_to_roman(DatumGetInt32(DirectFunctionCall1(numeric_int4, NumericGetDatum(x)))); } + else if (IS_EEEE(&Num)) + { + float8 val; + + if (Num.pre != 1) + ereport(ERROR, + (errcode(ERRCODE_SYNTAX_ERROR), + errmsg("invalid using of format EEEE"))); + + val = DatumGetFloat8(DirectFunctionCall1(numeric_float8, + NumericGetDatum(value))); + + numstr = orgnum = (char *) palloc(MAXDOUBLEWIDTH + 1); + len = snprintf(orgnum, MAXDOUBLEWIDTH + 1, "%.*e", Num.post, val); + if (len > Num.pre + Num.post + 5) + { + numstr = (char *) palloc(Num.pre + Num.post + 6); + fill_str(numstr, '#', Num.pre + Num.post + 5); + *(numstr + Num.pre) = '.'; + } + } else { Numeric val = value; *************** *** 4699,4704 **** --- 4756,4773 ---- */ if (IS_ROMAN(&Num)) numstr = orgnum = int_to_roman(value); + else if (IS_EEEE(&Num)) + { + float8 val = (float8) value; + + numstr = orgnum = (char *) palloc(MAXDOUBLEWIDTH + 1); + if (Num.pre != 1) + ereport(ERROR, + (errcode(ERRCODE_SYNTAX_ERROR), + errmsg("invalid using of format EEEE"))); + + snprintf(orgnum, MAXDOUBLEWIDTH + 1, "%.*e", Num.post, val); + } else { if (IS_MULTI(&Num)) *************** *** 4777,4782 **** --- 4846,4870 ---- numstr = orgnum = int_to_roman(DatumGetInt32( DirectFunctionCall1(int84, Int64GetDatum(value)))); } + else if (IS_EEEE(&Num)) + { + float8 val = (float8) value; + + numstr = orgnum = (char *) palloc(MAXDOUBLEWIDTH + 1); + if (Num.pre != 1) + ereport(ERROR, + (errcode(ERRCODE_SYNTAX_ERROR), + errmsg("invalid using of format EEEE"))); + + len = snprintf(orgnum, MAXDOUBLEWIDTH + 1, "%.*e", Num.post, value); + + if (len > Num.pre + Num.post + 5) + { + numstr = (char *) palloc(Num.pre + Num.post + 6); + fill_str(numstr, '#', Num.pre + Num.post + 5); + *(numstr + Num.pre) = '.'; + } + } else { if (IS_MULTI(&Num)) *************** *** 4851,4856 **** --- 4939,4962 ---- if (IS_ROMAN(&Num)) numstr = orgnum = int_to_roman((int) rint(value)); + else if (IS_EEEE(&Num)) + { + numstr = orgnum = (char *) palloc(MAXDOUBLEWIDTH + 1); + if (Num.pre != 1) + ereport(ERROR, + (errcode(ERRCODE_SYNTAX_ERROR), + errmsg("invalid using of format EEEE"))); + + if (isnan(value) || is_infinite(value)) + { + numstr = (char *) palloc(Num.pre + Num.post + 6); + fill_str(numstr, '#', Num.pre + Num.post + 5); + *(numstr + Num.pre) = '.'; + } + else + snprintf(orgnum, MAXDOUBLEWIDTH + 1, "%.*e", Num.post, value); + + } else { float4 val = value; *************** *** 4922,4932 **** char *numstr, *orgnum, *p; - NUM_TOCHAR_prepare; if (IS_ROMAN(&Num)) numstr = orgnum = int_to_roman((int) rint(value)); else { float8 val = value; --- 5028,5054 ---- char *numstr, *orgnum, *p; NUM_TOCHAR_prepare; if (IS_ROMAN(&Num)) numstr = orgnum = int_to_roman((int) rint(value)); + else if (IS_EEEE(&Num)) + { + numstr = orgnum = (char *) palloc(MAXDOUBLEWIDTH + 1); + if (Num.pre != 1) + ereport(ERROR, + (errcode(ERRCODE_SYNTAX_ERROR), + errmsg("invalid using of format EEEE"))); + + len = snprintf(orgnum, MAXDOUBLEWIDTH + 1, "%.*e", Num.post, value); + + if (isnan(value) || is_infinite(value) || len > Num.pre + Num.post + 5) + { + numstr = (char *) palloc(Num.pre + Num.post + 6); + fill_str(numstr, '#', Num.pre + Num.post + 5); + *(numstr + Num.pre) = '.'; + } + } else { float8 val = value; *** ./src/test/regress/expected/float8.out.orig 2009-04-10 18:09:10.000000000 +0200 --- ./src/test/regress/expected/float8.out 2009-04-10 18:10:09.000000000 +0200 *************** *** 438,440 **** --- 438,453 ---- | -1.2345678901234e-200 (5 rows) + -- support for EEEE format + SELECT to_char(1.2345678901,'9.999999EEEE'); + to_char + -------------- + 1.234568e+00 + (1 row) + + SELECT to_char(1.234567,'9.999EEEE'); + to_char + ----------- + 1.235e+00 + (1 row) + *** ./src/test/regress/sql/float8.sql.orig 2009-04-10 18:07:52.000000000 +0200 --- ./src/test/regress/sql/float8.sql 2009-04-10 18:09:49.000000000 +0200 *************** *** 167,169 **** --- 167,172 ---- SELECT '' AS five, * FROM FLOAT8_TBL; + -- support for EEEE format + SELECT to_char(1.2345678901,'9.999999EEEE'); + SELECT to_char(1.234567,'9.999EEEE');
-- Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org) To make changes to your subscription: http://www.postgresql.org/mailpref/pgsql-hackers