12

When I execute this code it returns me 1610612736

void main(){
float a=3.3f;
int b=2;
printf("%d",a*b);
}

Why and how to fix this ?

edit : It's not even a matter of integer and float, if i replace int b=2: by float b=2.0f it return the same silly result

Wicelo
  • 2,358
  • 2
  • 28
  • 44
  • It is a matter of integer and float - see my answer. – Carl Norum Jun 12 '13 at 04:34
  • @Carl is right. It may not be a float/int problem with the multiplication itself but it _definitely_ is in the format string. – paxdiablo Jun 12 '13 at 04:36
  • The function `printf` is a *varargs* method, with signature `int printf ( const char * format, ... )`. This means that it takes arbitrary arguments after the first, and it cannot check them at compile time or *cast them to a desired type taken from the format string*. Your format string says `%d`, which looks for an `int`. The expression `a*b` is `float`, which gets converted to `double`. These types don't even have the same memory size, so the temporary `double` gets physically cut in half and treated as an `int`. This is not a Solomonic solution. – Eric Jablow Jun 12 '13 at 04:38
  • possible duplicate of [Arduino sprintf float not formatting](http://stackoverflow.com/questions/27651012/arduino-sprintf-float-not-formatting) –  May 12 '15 at 18:04

2 Answers2

19

The result of the multiplication of a float and an int is a float. Besides that, it will get promoted to double when passing to printf. You need a %a, %e, %f or %g format. The %d format is used to print int types.

Editorial note: The return value of main should be int. Here's a fixed program:

#include <stdio.h>

int main(void)
{
    float a = 3.3f;
    int b = 2;
    printf("%a\n", a * b);
    printf("%e\n", a * b);
    printf("%f\n", a * b);
    printf("%g\n", a * b);
    return 0;
}

and its output:

$ ./example 
0x1.a66666p+2
6.600000e+00
6.600000
6.6
Carl Norum
  • 219,201
  • 40
  • 422
  • 469
  • 2
    Wow, `%a` must be in the running for the "most useless format specifier in a printf role" award :-) – paxdiablo Jun 12 '13 at 04:34
  • 9
    It's great! You can transfer (binary) floating point numbers 100% accurately via strings by using it, even to systems that don't use IEEE754. It preserves all of the bits of precision in a completely unambiguous way. Users probably don't care to see it, though.... – Carl Norum Jun 12 '13 at 04:35
  • 3
    Now _that's_ a use case I hadn't considered. Good call. – paxdiablo Jun 12 '13 at 04:37
  • 1
    First time seing %a! Except for debug purpose, i dont really see the use for it. – Phong Jun 12 '13 at 04:38
4

Alternately, you could also do

printf("%d\n", (int)(a*b));

and this would print the result you're (kind of) expecting.

You should always explicitly typecast the variables to match the format string, otherwise you could see some weird values printed.

krthkr
  • 76
  • 4