简体   繁体   中英

Float and double in C

Is the output correct for the following programs? I am using a Cygwin64 GCC compiler on a X86_64 Windows system. The architecture is little endian.

#include <stdio.h>

int main(int argc, char *argv[])
{
    int i = 0;
    float floatVal = 0x12345678;
    do
    {
        printf("Hello World %f\n", floatVal);
        floatVal++;
        i++;
    } while ( i < 10 );
    return 0;
}

Hello World 305419904.000000
Hello World 305419904.000000
Hello World 305419904.000000
Hello World 305419904.000000
Hello World 305419904.000000
Hello World 305419904.000000
Hello World 305419904.000000
Hello World 305419904.000000
Hello World 305419904.000000
Hello World 305419904.000000

Question 1: However this website gives me a completely different answer: http://www.binaryconvert.com/result_float.html?hexadecimal=12345678

Question 2: Why is the value not incrementing? The increments happen however if I use double instead of float.

What am I doing wrong?


Edit, after getting the correct answers:

After getting the correct answers from unwind, I have a further question and to do the same in Java. Since Java, does not use unions, is there a way to do the conversion from integer to float the same way as the accepted answer in C. I found the answer here :

How can I get/set individual bits in a float?

You're expecting the integer literal ( 0x12345678 ) to be used to set the bits of the float , but that isn't what happens.

Instead you get the actual integer ( 0x12345678 is 305419896 in decimal); your code is exactly the same as if it had said

float floatVal = 305419896;

The hexadecimal number is just an integer, that it's hex has no special meaning.

To do what you want, you'd to use an actual hexadecimal float constant perhaps, but that's a bit complicated.

You can use a union to the bits in there:

const union {
 int integer;
 float real;
} pair = { .integer = 0x12345678 };
float floatVal = pair.real;

Note that the above is undefined if the sizes mismatch, and also (as you seem to be aware) endian-specific.

If you print using %e or %g you will get the result you expect:

printf("%g\n", floatVal);

prints 5.69046e-28 on ideone.com.

Firstly you're confused between the hex value of an integer literal (which gets converted to a float) and the hex representation of a float. 0x12345678 == 305419904 .

As for the increment of a float using ++ seemingly not working as expected - this is simply due to the finite precision of a single precision floating point representation. If you start with a smaller number then you will see the expected behaviour:

 float f = 1.0f;  // f = 1.0
 f++;             // f = 2.0

However in your example:

 float f = 305419904.0f;  // f = 305419904.0
 f++;                     // f = 305419904.0

Note that using double will give the correct result for this case:

 double g = 305419904.0;  // g = 305419904.0
 g++;                     // g = 305419905.0

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM