Any differences with %.1f and %.01f? - c

When i compiles a program with this code:
int main()
{
float a;
scanf("%f", &a);
printf("%.1f\n", a); //Here
return 0;
}
There is no difference with this other:
int main()
{
float a;
scanf("%f", &a);
printf("%.01f\n", a); //Here
return 0;
}
Anybody can tell me why?

The number behind the period is the precision that specifies the number of digits after the decimal point of a floating-point value. The leading zero has no meanings.
The number before the period is the number that specifies the minimum field width. The leading zero will change the padding character from white space to 0.

The digits after the decimal point specify the precision - the minimum number of digits which will be written. .1 and .01 both say to put at least 1 digit, and to pad the result with zeros if there is fewer than 1 digit. Plain %f is equivalent to %.6f, i.e. 6 digits after the decimal point.

the output of first program will be for eg. a=100
for the both print command it would be
100.000000 (by default presicion of double is 6)
100.0
only.
where as the second program will have the value:
100.000000 (by default presicion of double)
100.0

Related

dynamically set decimal separator in number/string using c programming

i am facing problem while placing decimal point in my input string.please refer my code for better understanding.
Description:The field shall be eight (8) digits in width, right-aligned, zero-filled. Left most digit denotes the number of positions the decimal separator shall be move from the right.
Expected result should be like this :
example 1: 71234567
output 0.1234567
example 2 : 31234567
output : 1234.567
But when i run my code with above example i am getting below output.
output 1 : 0.123457
output 2 : 1234.567000
It should not need to append the zeroes in right hand side.why this is happening.could anyone please tell me.
Attached my code snippet:
#include<stdio.h>
#include<string.h>
#include<math.h>
#include<stdlib.h>
int main()
{
unsigned char str[8] = "31234567";
int num = atoi(str); //Convert string to int
printf("num = %d\n",num);
int FirstDigit = num;
num = num % (unsigned long)pow(10.0, (double)floor(log10(num)));
printf("After removing 1st digit from number = %d\n",num);
while(FirstDigit>=10)
{
FirstDigit = FirstDigit/10;
}
printf("Decimal position stored in FirstDigit = %d\n",FirstDigit);
printf("Final value = %f",num/pow(10,FirstDigit));
return 0;
}
For default printf gives 6 significant digits, if precision is not specified.
https://man7.org/linux/man-pages/man3/printf.3.html
g, G The double argument is converted in style f or e (or F or
E for G conversions). The precision specifies the number
of significant digits. If the precision is missing, 6
digits are given; if the precision is zero, it is treated
as 1. Style e is used if the exponent from its conversion
is less than -4 or greater than or equal to the precision.
Trailing zeros are removed from the fractional part of the
result; a decimal point appears only if it is followed by
at least one digit.
In your case you are trying to print the number 0.1234567 but in that number there are 7 significant digits. So printf rounds that number to 0.123457. You can specify precision like this.
printf("Final value = %.7f",num/pow(10,FirstDigit)); // (%.7f)
But you also want to get rid of the trailing zeros. For this you can use it like this.
printf("Final value = %.10g",num/pow(10,FirstDigit)); // (%.10g)
I specified precison as 10 because you are using int. Hence int can have at most 10 digits.

How to set the level of precision for the decimal expansion of a rational number

I'm trying to print out the decimal expansion of a rational number in C. The problem I have is that when I divide the numerator by the denominator I lose precision. C rounds up the repeating part when I don't want it to.
For example, 1562/4995 = 0.3127127127... but in my program I get 1562/4995 = 0.312713. As you can see a part of the number that I need has been lost.
Is there a way to specify C to preserve a higher level of decimal precision?
I have tried to declare the result as a double, long double and float. I also tried to split the expansion into 2 integers seperated by a '.'
However both methods haven't been successful.
int main() {
int numerator, denominator;
numerator = 1562;
denominator = 4995;
double result;
result = (double) numerator / (double) denominator;
printf("%f\n", result);
return 0;
}
I expected the output to be 1562/4995 = 0.3127127127... but the actual output is 1562/4995 = 0.312713
The %f format specifier to printf shows 6 digits after the decimal point by default. If you want to show more digits, use a precision specifier:
printf("%.10f\n", result);
Also, the double type can only accurately store roughly 16 decimal digits of precision.
You need to change your output format, like this:
printf("%.10lf\n", result);
Note two things:
The value after the . specifies the decimal precision required (10 decimal places, here).
Note that I have added an l before the f to explicitly state that the argument is a double rather than a (single-precision) float.
EDIT: Note that, for the printf function, it is not strictly necessary to include the l modifier. However, when you come to use the 'corresponding' scanf function for input, it's absence will generate a warning and (probably) undefined behaviour:
scanf("%f", &result); // Not correct
scanf("%lf", &result); // Correct
If printing is all you want to do, you can do this with the same long division you were taught in elementary school:
#include <stdio.h>
/* Print the decimal representation of N/D with up to
P digits after the decimal point.
*/
#define P 60
static void PrintDecimal(unsigned N, unsigned D)
{
// Print the integer portion.
printf("%u.", N/D);
// Take the remainder.
N %= D;
for (int i = 0; i < P && N; ++i)
{
// Move to next digit position and print next digit.
N *= 10;
printf("%u", N/D);
// Take the remainder.
N %= D;
}
}
int main(void)
{
PrintDecimal(1562, 4995);
putchar('\n');
}

Why does pow(x,y) return inf when x and y are chars?

I understand how to use pow() correctly I'm just wondering why when I run this code ans = inf.
I am having a hard time understanding this.
Does this have anything to do with chars only being able to take on the values -128 to +127 and the way pow() is calculated?
Does this have anything to do with the space in " %c" as in my first scanf param?
Linux 4.9.0-7-amd64
debian 4.9.110-1
gcc version 6.3.020170516
#include <stdio.h>
#include <math.h>
int main ()
{
char base, exp;
float ans;
printf("Enter base number : ");
scanf(" %c", &base);
printf("Enter exp number : ");
scanf(" %c", &exp);
ans = pow(base,exp);
printf("%c raised to the %c power equals %f", base, exp, ans);
return 0;
}
When you enter base and exp using %c you get the characters '0' - '9', not the integer values. So if you enter 0 and 0, the values you get (assuming ASCII encoding) will actually by 48, since that is the ASCII code for '0'. The result of 4848 is roughly 5 x 1080.
You then save the resulting value in a float. Assuming a float is IEEE754 single precision, it can hold an exponent no larger that +/- 38. So you're attempting convert an out-of-range value which invokes undefined behavior, meaning the result is unpredictable. If you changed the type of ans to double you would see the actual result.
Base and exp is not the integer values (0-9). So you want to enter "%d". Not the " %c"

Why do I get different results only 1% of the time?

I am trying to truncate everything past the hundredths decimal. (13.4396 would be 13.43) Sholdn't it always or never work?
I have this formula that works 99%:
input = (( (double) ((int)(orgInput * 100)) ) / 100) ;
Then I have this formula sequence that is arithmetically equivalent:
input = (orgInput * 100);
input = (int) input;
input = (double) (input);
input = input / 100;
These inputs do not give the desired result (Formula truncates and round down, while the broken down steps output the desired result):
12.33
99.99
22.22
44.32
56.78
11.11
And then an even bigger mystery to me is why 33.30 does not work on either of them. Below is my program that runs continuously to demonstrate my problem.
#include <stdio.h>
#include <stdlib.h>
int main(void)
{
double orgInput, input;
while (4!=3)
{
printf("Please enter the dollar amount (up to $100) => ");
scanf("%lf", &orgInput);
/* Truncates anything past hundredths place */
input = (orgInput * 100) ;
printf("\n1. input is %g \n ", input);
input = (int) input ;
printf("\n2. input is %g \n ", input);
input = (double) (input) ;
printf("\n3. input is %g \n", input);
input = input / 100 ;
printf("\n4. input is %.2lf \n", input);
input = (( (double) ((int)(orgInput * 100)) ) / 100) ;
printf("\nUsing the formula the input is %.2lf \n \n\n", input);
}
system("PAUSE");
return 0;
}
Thank you in advance!!!! P.S. Sorry for the formatting I am still getting used to stackoverflow
Key phrases:
Double to int conversion
Precision error
I think you are suffering from floating-point precision errors.
You should be able to fix this by doing:
const double epsilon = 1e-10; // Or some suitable small number
input = floor(orgInput * 100 + epsilon) / 100;
An alternative is to stop this from happening on input. Instead of reading in a double, you read a string and then parse that to get out the dollar and cents amount (cents being exactly 2 digits following the decimal point, if any). You can then ignore everything else.
In general, if you are working with money truncated to cents, you might be best to keep it in cents and use integers. Either that or round instead of truncate (for my above example, that would mean an epsilon of 0.5).
You need to understand that floats are represented in binary as:
2^(exponent) * mantissa
Exponent is a standard integer, but mantissa (a value between 1 and 2) is a number of bits where each bit represents a fraction: 1, 1/2, 1/4, 1/8, 1/16 and so on... Therefore it is not possible for the mantissa to represent certain values exactly, it will have an accuracy of +/- some fraction.
For example you mentioned 33.30. As a float 33.30 can only be: 2^5 * mantissa.
In this case the mantissa has to be 33.30/32 = 1.40625 exactly. But by making it out of the fractions the closest it can be is be is: 1.0406249999999999111821580299874767661094. So the actual value of the double is not 33.30, its 33.2999999999999971578290569595992565155029296875, which of course rounds DOWN to 33.29 when you do the type cast to integer.
The correct way to fix your program is not to scan in a float in the first place. You should be scanning in two integers seperated by decimal, and if scanf returns a value that indicates it did not scan two integers, then scan it as one integer for the case of a dollar only value.
Sadly, printf works by conversions to ints inside it and will not properly print any double precision floats that have more than 6 decimal places, which is why you see it as 33.30 even through you are asking printf to print the value of a double.
Most machines use binary, not decimal floating point. While binary-to-decimal conversion always gives exact values (in theory), it's impossible to convert from decimal to binary without rounding (I'm not considering the impractical case when numbers can have infinite number of digits).
As such, all your binary floating-point numbers are going to be slightly off of what they would've been in decimal.
The only 1-digit decimal fractions that can be represented in binary are: .0, .5.
Likewise, 2-digit decimal fractions exactly representable in binary are: .00, .25, .50, .75 (see here).
If you want, which I doubt, you can round to the nearest fraction of the four.

Is it possible to round a double using just a printf statement?

Obviously this is just a fraction of the code.
printf("Please enter a positive number that has a fractional part with three or more decimal places\n");
scanf("%5.2d", &x);
printf("The number you have entered is %5.2d\n" ,x);
Would this automatically round the number I type in? Or is there another way to do this?
Edit:
printf("Please enter a positive number that has a fractional part with three or more decimal places\n");
scanf("%lf", &x);
x = x + 0.05;
printf( "The number you have entered is %5.2lf\n", x);
Iv done this, but Im taking into consideration what someone had said about printf just "changing" the way it reads out. So this is obviously not the right way. Should I implement maybe the pow() function? Will that work with this somehow?
Edit2:
printf("Please enter a positive number that has a fractional part with three or more decimal places\n");
scanf("%lf", &x);
x = x + 0.05;
printf( "The number you have entered is %5.2lf\n", x);
Okay, iv gotten to the point where if i imput a number it will round to a whole number. 35.21 will round to 35, and 35.51 will round to 36 et. etc.
How would I get 35.2178 to round to 35.22, and 35.2135 to round to 35.21.
How would I get the certain powers of the decimal to round instead of the whole number?
You really, really should not store "rounded" values in floating point variables. Floating point inaccuracy will ruin this - your 5.10 might become 5.099999999941892 simply because the implementation might not be able to store 5.10 exactly.
As an alternative, read the whole number, multiply it with 100 and convert it to int (which will round it towards zero). That will keep your calculations accurate.
"%.2f" will round a double to 2 digits. A double is not an integer, and %d and %f are not interchangeable.
{
float x;
float rounded_x;
printf("Please enter a positive number that has a fractional part with three or more decimal places\n");
scanf("%f", &x);
rounded_x = ((int)(x * 100 + .5) / 100.0);
printf( "The number you have entered is %.2f\n", rounded_x);
return 0;
}
Thank you to everyone who tried to help! I finally got it
printf won't change the value of the number, just how it is displayed. An alternative is
#include <math.h>
// round double x to 2 decimal places
x = 0.01 * floor(x * 100.0 + 0.5);
This doesn't make sense
scanf("%5.2d", &x);
You can't have an integer with numbers after the decmal point. if x is a flat then weird things will happen. If its an integer why are you after 2 decimal places in the printf.
What exactly are you trying to do?
Edit:
double x;
printf( "Please enter a positive number that has a fractional part with three or more decimal places\n" );
scanf( "%lf", &x );
printf( "The number you have entered is %5.2f\n", x + 0.005 );
I'm pretty sure printf only truncates. So you will need to add 0.005 to round it.

Resources