Почему scanf() нуждается в ”%lf" для удвоения, когда printf() подходит только для "%f”?

StackOverflow https://stackoverflow.com/questions/210590

  •  03-07-2019
  •  | 
  •  

Вопрос

Почему это происходит scanf() нуждается в l в "%lf" при чтении double, когда printf() можно использовать "%f" независимо от того , является ли его аргумент double или float?

Пример кода:

double d;
scanf("%lf", &d);
printf("%f", d);
Это было полезно?

Решение

Потому что C преобразует значения float в double для функций, которые принимают переменные аргументы.Указатели ни на что не рекламируются, поэтому вы должны использовать %lf, %lg или %le (или %la в C99) для чтения в двойном формате.

Другие советы

Начиная с С99, соответствие между спецификаторами формата и типами аргументов с плавающей запятой в C согласуется между printf и scanf.Это так

  • %f для float
  • %lf для double
  • %Lf для long double

Просто так получилось, что когда аргументы типа float передаются как переменные параметры, такие аргументы неявно преобразуются в тип double.Это причина, по которой в printf спецификаторы формата %f и %lf являются эквивалентными и взаимозаменяемыми.В printf вы можете "перекрестно использовать" %lf с float или %f с double.

Но нет никаких причин делать это на практике.Не используйте %f Для printf аргументы типа double.Это широко распространенная привычка, зародившаяся еще во времена C89 / 90, но это плохая привычка.Использование %lf в printf для double и продолжай %f зарезервировано для float аргументы.

scanf необходимо знать размер данных, на которые указывает &d чтобы заполнить его должным образом, в то время как вариационные функции увеличивают значения float до double (не совсем уверен, почему), так что printf всегда получает double.

Потому что в противном случае scanf подумает, что вы передаете указатель на значение с плавающей точкой, размер которого меньше, чем double , и вернет неверное значение.

Использование либо значения с плавающей запятой, либо двойного значения в выражении C приведет к получению значения, которое в любом случае является двойным, поэтому printf не сможет определить разницу.Принимая во внимание, что указатель на double должен быть явно передан scanf в отличие от указателя на float, потому что важно то, на что указывает указатель.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top