Почему printf печатает неправильные значения? - PullRequest
4 голосов
/ 07 сентября 2010

Почему я получаю неправильные значения при печати int с использованием printf("%f\n", myNumber)?

Я не понимаю, почему он печатается нормально с %d, но не с %f.Разве это не должно просто добавить дополнительные нули?

int a = 1;
int b = 10;
int c = 100;
int d = 1000;
int e = 10000;

printf("%d %d %d %d %d\n", a, b, c, d, e);   //prints fine
printf("%f %f %f %f %f\n", a, b, c, d, e);   //prints weird stuff

Ответы [ 7 ]

14 голосов
/ 07 сентября 2010

ну, конечно, это печатает "странные" вещи. Вы проходите через int с, но сообщаете printf, что вы прошли через float с. Поскольку эти два типа данных имеют разные и несовместимые внутренние представления, вы получите «бред».

Не существует «автоматического приведения», когда вы передаете переменные в переменную функцию, например printf, значения передаются в функцию как тип данных, которым они на самом деле являются (или в некоторых случаях обновляются до более совместимого типа). 1007 *

То, что вы сделали, похоже на это:

union {
    int n;
    float f;
} x;

x.n = 10;

printf("%f\n", x.f); /* pass in the binary representation for 10, 
                        but treat that same bit pattern as a float, 
                        even though they are incompatible */
4 голосов
/ 07 сентября 2010

Если вы хотите напечатать их как числа с плавающей точкой, вы можете привести их как числа с плавающей точкой перед передачей их функции printf.

printf("%f %f %f %f %f\n", (float)a, (float)b, (float)c, (float)d, (float)e);
3 голосов
/ 07 сентября 2010

a, b, c, d и e не являются поплавками.printf () интерпретирует их как плавающие, и это выведет на экран странные вещи.

2 голосов
/ 07 сентября 2010

Использование неверного спецификатора формата в printf() вызывает Undefined Behaviour

Например:

 int n=1;
 printf("%f", n); //UB

 float x=1.2f;
 printf("%d", x); //UB

 double y=12.34;
 printf("%lf",y); //UB 

Примечание: спецификатор формата для double в printf() равен %f.

1 голос
/ 07 сентября 2010

проблема ... внутри printf.происходит следующее

if ("%f") {
 float *p = (float*) &a;
 output *p;  //err because binary representation is different for float and int
}
0 голосов
/ 07 сентября 2010

Для «нормальных» (не переменных функций со всеми указанными типами) компилятор преобразует целочисленные типы в типы с плавающей запятой, где это необходимо.

Этого не происходит с аргументами variadac, которые всегда передаются "как есть".

0 голосов
/ 07 сентября 2010

способ работы аргументов printf и переменных заключается в том, что спецификатор формата в строке, например "% f% f", сообщает типу printf тип и, следовательно, размер аргумента.Указав неверный тип для аргумента, он запутается.

посмотрите в stdarg.h макросы, используемые для обработки переменных аргументов

...