Каков правильный спецификатор формата double
в printf? Это %f
или это %lf
? Я верю %f
, но я не уверен.
Пример кода
#include <stdio.h>
int main()
{
double d = 1.4;
printf("%lf", d); // Is this wrong?
}
c
floating-point
printf
double
format-specifiers
леопард
источник
источник
"%lf"
не определено; в библиотеках C99 и C11 он определен так же, как"%f"
.%lf
правильный формат формата дляdouble
. Но так стало в C99. До этого нужно было использовать%f
.Ответы:
"%f"
(или хотя бы один) правильный формат для двойного числа. Там нет не формат дляfloat
, потому что если вы попытаетесь пропускатьfloat
кprintf
, он будет назначен ,double
прежде чемprintf
его получит 1 ."%lf"
также допустимо в соответствии с текущим стандартом -l
оно указано как не имеющее эффекта, если за ним следуетf
спецификатор преобразования (среди прочих).Обратите внимание, что это единственное место, где
printf
строки формата существенно отличаются отscanf
(иfscanf
т. Д.) Строк формата. Для вывода, вы передаете значение , которое будет повышен сfloat
до ,double
когда передается в качестве параметра VARIADIC. Для ввода вы передаете указатель , который не продвигается, поэтому вы должны указатьscanf
, хотите ли вы прочитать afloat
или adouble
, так какscanf
,%f
означает, что вы хотите прочитать a,float
и%lf
означает, что вы хотите прочитать adouble
(и, для чего это стоит, дляlong double
, вы используете%Lf
для либоprintf
илиscanf
).1. C99, §6.5.2.2 / 6: «Если выражение, которое обозначает вызываемую функцию, имеет тип, который не включает в себя прототип, целочисленные преобразования выполняются для каждого аргумента, а аргументы, имеющие тип float, повышаются до двойного. Это называется продвижением аргументов по умолчанию. " В C ++ формулировка несколько иная (например, она не использует слово «прототип»), но эффект тот же: все переменные параметры проходят промоакции по умолчанию, прежде чем они будут получены функцией.
источник
g++
отклоняет%lf
при компиляции с-Wall -Werror -pedantic
:error: ISO C++ does not support the ‘%lf’ gnu_printf format
l
было расширением. Стандарты C99 / 11 и C ++ 11 требуют, чтобы реализация позволила это.scanf
делает покупкуdouble
s лице%lf
: она жалуется , что ожидалосьfloat *
и нашелdouble *
только с%f
.scanf
принимает указатели , где хранить то , что он читает, поэтому потребность знать , насколько большим являются пространство указываемым на это, в то время какprintf
принимает сами значения, а «акцию аргументов по умолчанию» означает , как в конечном итоге , какdouble
с, так чтоl
это по сути необязательно.Учитывая стандарт C99 (а именно, черновик N1256 ), правила зависят от вида функции: fprintf (printf, sprintf, ...) или scanf.
Вот соответствующие извлеченные части:
fprintf
Применяются те же правилаprintf
, чтоsprintf
и для похожих функций.Короче говоря, для
fprintf
следующих спецификаторов и соответствующих типов указаны:%f
-> двойной%Lf
-> длинный двойной.и для
fscanf
этого есть:%f
-> плавать%lf
-> двойной%Lf
-> длинный двойной.источник
Это может быть
%f
,%g
или в%e
зависимости от того, как вы хотите, чтобы число было отформатировано. Смотрите здесь для более подробной информации.l
Модификатор требуетсяscanf
сdouble
, но не вprintf
.источник
l
(нижний регистр) модификатор для целочисленных типов ( cplusplus.com/reference/clibrary/cstdio/printf ) иL
для типов с плавающей запятой. Кроме того,L
модификатор ожидает, аlong double
не простойdouble
.l
не требуется вprintf
течениеdouble
.Формат
%lf
- это совершенно правильныйprintf
форматdouble
, именно так, как вы его использовали. Нет ничего плохого в вашем коде.Формат
%lf
inprintf
не поддерживался в старых (до C99) версиях языка C, что создавало поверхностную «несогласованность» между спецификаторами формата дляdouble
inprintf
иscanf
. Это поверхностное несоответствие было исправлено в C99.Вы не обязаны использовать
%lf
сdouble
вprintf
. Вы также можете использовать%f
, если вы так предпочитаете (%lf
и%f
эквивалентны вprintf
). Но в современном C имеет смысл предпочесть использовать%f
сfloat
,%lf
сdouble
и%Lf
сlong double
, последовательно в обоихprintf
иscanf
.источник
scanf()
,"%f"
,"%lf"
Совпадениеfloat *, double *
, неfloat, double
как следует из последней строки.%Lf
(обратите внимание на заглавнуюL
) это спецификатор формата для длинных двойников .Для равнины
doubles
, либо%e
,%E
,%f
,%g
или%G
будут делать.источник
%g
а%G
?