mnyfmt.c: Format money or currency amounts
Functions
mnyfmt.c File Reference

Implementation for mnyfmt(). More...

#include "mnyfmt.h"

Go to the source code of this file.

Functions

char * mnyfmt (char *fmtstr, char dec, mnyfmt_long moneyval, unsigned CE)
 Formats and stores in fmtstr the money amount. More...
 

Detailed Description

Implementation for mnyfmt().

Author
Adolfo Di Mare adolf.nosp@m.o@di.nosp@m.-mare.nosp@m..com
Date
2011

Definition in file mnyfmt.c.

Function Documentation

char* mnyfmt ( char *  fmtstr,
char  dec,
mnyfmt_long  moneyval,
unsigned  CE 
)

Formats and stores in fmtstr the money amount.

Before invocation, the formatting pattern (picture clause) is stored in result string fmtstr. To avoid using (double) values that have many round off problems, the parameter for this function is an integer scaled to 10^CE digits. For example, when using CE==2 digits, the monetary value "$2,455.87" is representad by the integer '245587', and if CE==4 digits are used, the integer value would be '24558700'.

  • The (integer) value to format is moneyval.
  • Overwrites fmtstr with the formatted value.
  • On error, leaves fmtstr untouched and returns (char*)(0).
  • If the fmtstr does not have enough format characters '9' for the integer part to format, of if the '-' cannot fit on top of a '9' character, fmtstr remains untouched and the value returned is (char*)(0).
  • The valid range for CE, the 'currenct exponent', is [0..6] [ a CE of 7 or bigger leaves fmtstr untouched and the value returned is (char*)(0) ].
  • The first occurrence of the character dec is the decimal fraction separator (usually '.' or ',').
  • When the decimal fraction separator character dec does not appear in fmtstr it is assumed to be '\0' (end of string character).
  • After the dec separator all the leading consecutive '9' format characters are substituted with the corresponding digit from the decimal part in moneyval, using digit zero '0' as fill character.
  • All digits that inmediatly follow the decimal fraction separator are changed either to zero or to the corresponding digit taken from the decimal part in moneyval.
  • Both the integer part and the fractional part are filled with the digits that correspond to its position. This means that a format string like "9999.9999" wild yield "0123.8700" as result when moneyval==1238700 and CE==4.
  • Characters trailing after the dec separator that are not the '9' format digit are left untouched.
  • All format characters '9' appearing before the decimal separator dec will be replaced by digit zero '0' if the corresponding digit in moneyval is not significant.
  • When moneyval is negative, the '-' sign will be place over the '9' immediately before the more significant digit.
  • Non format characters in fmtstr are left untouched.
  • The negative sign always is '-' and it is always placed on top of the corresponding format character.
  • Returns (char*)(0) when the formatted value does not fit within strlen(fmtstr) characters.
  • Returns a pointer to the first significant digit in the formatted string, within fmtstr or to the '-' sign if the formatted value is negative.
  • Before storing the format string in fmtstr, the programmer must ensure that fmtstr is big enough to hold the format string.
Remarks
  • This routine basically substitutes each '9' character in fmtstr for its corresponding decimal digit, or '0' when it is not a significant digit. All other characters within fmtstr remain untouched.
  • As it happens with many C functions, before invocation the programmer must be sure that fmtstr is big enough to copy on it the complete format string, as otherwise memory beyond fmtstr would be overwritten.
  • There is no (wchart_t) version for this function, as it is meant to place digits in a formatting string. After placement, the result string can be converted to other forms.
1 {{ // test.example
1  // (2^128 < 10^40) && (2*40<96) ==> char[96] holds a
2  char *sgn, fmtstr[96],mem[96]; // 128 bit integer
3 
4  unsigned CE, ten_pow_CE;
5  CE = 2; ten_pow_CE = 100; // 10^CE -> "Currency Exponent"
6 
7  strcpy( mem, "USD$ " ); // Picture clause
8  strcpy( fmtstr , "99,999,999.99999" );
9  if (( sgn = mnyfmt( fmtstr , '.' ,-10245587,CE ) )) {
10  assertTrue( eqstr( fmtstr , "0-,102,455.87000") );
11  if ( (*sgn=='-') && (','==*(sgn+1)) ) { ++sgn; *sgn='-'; }
12  assertTrue( eqstr( sgn, "-102,455.87000") );
13 
14  strcat( mem , sgn );
15  assertTrue( eqstr( mem, "USD$ -102,455.87000") );
16  }
17  else {
18  assertFalse( "ERROR [???]: " "-102,455.87000" );
19  }
20 }}

See also
mnyfmtts.c

Definition at line 102 of file mnyfmt.c.