-18

Why is the output of the following C code 0.000000?

#include <stdio.h>

void foo(float *);

int main()
{
    int i = 10, *p = &i;
    foo(&i);
}

void foo(float *p)
{
    printf("%f\n", *p);
}

Please explain your answer.

Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
user2653926
  • 610
  • 7
  • 23

4 Answers4

3

You are making printf() interpret the bits of an integer as if they were the bits of a float. This is undefined behavior.

What result did you expect?

Community
  • 1
  • 1
unwind
  • 391,730
  • 64
  • 469
  • 606
  • Why there was no type casting. I expected 10.000000 – user2653926 Oct 28 '15 at 10:09
  • 4
    @user2653926 When would that happen? There is no way for `foo()` to know that you lied. You should be getting compiler warnings however, since you're calling `foo()` with an argument of the wrong type. – unwind Oct 28 '15 at 10:10
  • Sorry still dont get it. – user2653926 Oct 28 '15 at 10:14
  • To start with you are sending an int into a function that takes a float. What compiler warnings/errors are you getting? Always try to hear what the compiler is saying about your code. So change the type of i to float and you are on your way to a better place... – mattiash Oct 28 '15 at 10:28
1

First of all, when your code looks like it does in your question the line *p = &i; doesn't do anything at all.

Next - you are passing a pointer to your int variable to a function that expects float. Like @unwind mentioned in the comments there is no way for foo() to know that you lied. Typecasting is different thing from what you seem to consider it.

#include <stdio.h>
void foo(float *);
int main()
{
    int i = 10; //try this and see it fails, 
                //then switch this line with float i = 10; and try again
    foo(&i);
}
void foo(float *p)
{
    printf("%f\n", *p);
}

EDIT> If you insist on having a typecast somewhere...

#include <stdio.h>
void foo(float *);
int main()
{
    int i = 10;
    float p = (float)i;
    foo(&p);
    return 0;
}
void foo(float *p)
{
    printf("%f\n", *p);
}
Rorschach
  • 734
  • 2
  • 7
  • 22
0

Variadic functions in C and C++ take variable number of arguments while they don't know type of entry arguments.

In printf function, the first argument is a string which hopefully indicates the types of following arguments by format specifiers.

In your code, your specifier indicates that the following argument is an float (%f), but you've passed an integer. Since all this type checking is happening in run-time and compiler knows nothing about it, there is no automatic casting.

Your code invokes undefined behavior.

masoud
  • 55,379
  • 16
  • 141
  • 208
  • The actual parameter has static type `float`. Its runtime behavior is defined because of a strict aliasing rule violation. But the problem is not with the variadic function call. One could write `float x = *p;` and the problem would still be there. – Ben Voigt Apr 30 '18 at 06:39
0

Try this one:

#include <stdio.h>
void foo(int *);
int main()
{
    int i = 10;
    foo(&i);
}
void foo(int *p)
{
    printf("%f\n",(float) *p);
}
Newaz Hossain
  • 157
  • 1
  • 4