I compiled the following program with gcc 4.4.1 and I get unexpected output (Well, unexpected for me)
#include<stdio.h>
int main()
{
float x=0.3, y=0.7;
if(x==0.3)
{
if(y==0.7)
printf("Y\n\n");
else
printf("X\n\n");
}
else
printf("NONE\n\n");
}
Output: NONE
#include<stdio.h>
int main()
{
float x=0.3, y=0.7;
if(x<0.3)
{
if(y==0.7)
printf("Y\n\n");
else
printf("X\n\n");
}
else
printf("NONE\n\n");
}
Output: NONE
#include<stdio.h>
int main()
{
float x=0.3, y=0.7;
if(x>0.3)
{
if(y>0.7)
printf("Y\n\n");
else
printf("X\n\n");
}
else
printf("NONE\n\n");
}
Output:X
So, it’s clearly visible that the stored value in “x” is greater than 0.3 and the stored value in “y” is less than 0.7
Why is this happening? Is this a property of float datatype or the if-else statements interpret float in a different way?
Thanks.
Edit: Alright, I pondered it over and I’m getting a little confused now. Kindly tell if my understanding of this problem is correct or not.
float x=0.3;
This stores x=0.30000001192092895508 in the memory. Clearly, this is greater than 0.3 (Is this correct?)
Now, double x=0.3 results in x=0.29999999999999998890 and this is smaller than 0.3 (Is this correct too?)
Main question:
So if I use store 0.3 in float x, then the following statement if(x>0.3) results in x=0.30000001192092895508 being implicitly casted as a double and 0.3 is also a double instead of a float. Hence 0.3=0.29999999999999998890 and the internal operation is if((double) 0.30000001192092895508 > (double) 0.29999999999999998890). Is this correct?
You’re using
floatfor storage, but you comparisons are being performed against the literals which are of typedouble.The values of
xandyaren’t exactly 0.3 and 0.7, as those numbers aren’t representable in binary floating point. It happens that the closestfloatto 0.3 is greater than the closestdoubleto 0.3, and the closestfloatto 0.7 is less than the closestdoubleto 0.7… hence your comparison results.Assuming the representations are the same as in C# (where I happen to have some tools to help) the values involved are:
So that explains why it’s happening… but it doesn’t explain how to work around the issue for whatever your code is actually trying to do, of course. If you can give more context to the bigger problem, we may be able to help more.