Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

printf a float value with precision (number of decimal digits) passed in a variable [duplicate]

I can print a float value with precision of 3 decimal digits with

double f = 1.23456;
printf( "%.3f", f );

Now I have the number of requested decimal digits that is not fixed but stored into a variable

int precision;
precision = atoi( argv[ 1 ] ); // ...just for example
double f = 1.23456;

How do I print the value of f with the number of decimal digits specified in precision ?

I can programmatically compose the format string for printf but I'm wondering if there is a more simple way to do it.

like image 668
Paolo Avatar asked Jan 31 '16 23:01

Paolo


1 Answers

Use ".*"

printf("%.*f", precision, f);

Example:

>>> printf("%.*f", 5, 3.14)
"3.14000"

Precision

This is called the precision field. According to the man pages,

The precision: An optional precision, in the form of a period ('.') followed by an optional decimal digit string. Instead of a decimal digit string one may write "*" or "*m$" (for some decimal integer m) to specify that the precision is given in the next argument, or in the m-th argument, respectively, which must be of type int. If the precision is given as just '.', or the precision is negative, the precision is taken to be zero. This gives the minimum number of digits to appear for d, i, o, u, x, and X conversions, the number of digits to appear after the radix character for a, A, e, E, f, and F conversions, the maximum number of significant digits for g and G conversions, or the maximum number of characters to be printed from a string for s and S conversions.

Width

The width field is similar and works for more formats, such as "%*s". Just remove the .. It will pad the output with spaces or zeros as needed. If precision is negative, the string will be left-aligned.

>>> printf("%*s\n", 10, "left?")
"     left?"
>>> printf("%*s\n", -10, "left?")
"left?     "

According to the man pages,

The field width: An optional decimal digit string (with nonzero first digit) specifying a minimum field width. If the converted value has fewer characters than the field width, it will be padded with spaces on the left (or right, if the left-adjustment flag has been given). Instead of a decimal digit string one may write "*" or "*m$" (for some decimal integer m) to specify that the field width is given in the next argument, or in the m-th argument, respectively, which must be of type int. A negative field width is taken as a '-' flag followed by a positive field width. In no case does a nonexistent or small field width cause truncation of a field; if the result of a conversion is wider than the field width, the field is expanded to contain the conversion result.

like image 182
Hugo O. Rivera Avatar answered Oct 21 '22 12:10

Hugo O. Rivera