正确的printf格式说明符为double

Leo*_*ard 451 c floating-point double printf format-specifiers

doubleprintf中正确的格式说明符是什么?是它%f还是它%lf?我相信它%f,但我不确定.

代码示例

#include <stdio.h>

int main()
{
   double d = 1.4;
   printf("%lf", d); // Is this wrong?
}
Run Code Online (Sandbox Code Playgroud)

Jer*_*fin 584

"%f"是double的(或至少一种)正确格式.有一个没有格式的float,因为如果你尝试将传递floatprintf,它会被提升到doubleprintf接受它1."%lf"在当前标准下也是可接受的 - l如果后面跟着f转换说明符(其中包括),则指定为无效.

请注意,这是一个printf格式字符串与scanf(和fscanf等)格式字符串大不相同的地方.对于输出,您将传递一个,该将从作为可变参数传递时传递floatdouble.对于输入,你传递的是一个未被提升的指针,所以你必须告诉scanf你是否想要读一个float或一个double,所以因为scanf,%f意味着你想读一个float并且%lf意味着你想读一个double(并且,为了它的内容)值得的,对于a long double,你%Lf用于printf或者scanf).


1. C99,§6.5.2.2/ 6:"如果表示被调用函数的表达式具有不包含原型的类型,则对每个参数执行整数提升,并将具有float类型的参数提升为double.这些被称为默认参数促销." 在C++中,措辞有些不同(例如,它不使用"原型"一词),但效果是相同的:所有可变参数在功能接收之前都经过默认促销.

  • 注意`g ++`在使用`-Wall -Werror -pedantic`编译时拒绝`%lf`:`错误:ISO C++不支持'%lf'gnu_printf格式` (7认同)
  • @EricDand那是因为`scanf`指向存储它所读取内容的指针,所以_needs_知道指向的空间有多大,而`printf`取值本身,而"默认参数促销"意味着两者都结束作为`double`s,所以`l`基本上是可选的. (4认同)
  • @kynan:如果是这样(至少假设是当前版本的 g++),那就是 g++ 中的一个错误。对于 C89/90 和 C++98/03,允许 `l` 是一个扩展。C99/11 和 C++11 标准要求实现允许它。 (2认同)

mlo*_*kot 62

鉴于C99标准(即N1256草案),规则取决于功能类型:fprintf(printf,sprintf,...)或scanf.

以下是提取的相关部分:

前言

第二版取消并取代了ISO/IEC 9899/COR1:1994,ISO/IEC 9899/AMD1:1995和ISO/IEC 9899/COR2:1996修订和更正的第一版ISO/IEC 9899:1990.上一版的主要变化包括:

  • %lf 转换说明符允许 printf

7.19.6.1 fprintf功能

7长度修饰符及其含义是:

l(ell)指定(...)对后续的a,A,e,E,f,F,g或G转换说明符没有影响.

L指定跟随a,A,e,E,f,F,g或G转换说明符适用于long double参数.

对于指定的规则同样fprintf适用于printf,sprintf和类似的功能.

7.19.6.2 fscanf功能

11长度修饰符及其含义是:

l(ell)指定(...)后面的a,A,e,E,f,F,g或G转换说明符适用于类型指针为double的参数;

L指定跟随a,A,e,E,f,F,g或G转换说明符适用于类型指针为long double的参数.

12转换说明符及其含义为:a,e,f,g匹配可选的带符号浮点数,(...)

14转换标识符A,E,F,G和X也是有效的和行为相同,分别为A,E,F,G和x.

长话短说,fprintf指定了以下说明符和相应的类型:

  • %f - >双
  • %Lf - >长双.

因为fscanf它是:

  • %f - >浮动
  • %lf - >双
  • %Lf - >长双.


vit*_*aut 21

它可以是%f,%g%e取决于您希望如何格式化数字.有关详细信息,请参见此处 l修正是必需的scanfdouble,但不是在printf.

  • user470379:那么与我的答案相矛盾的是什么?我没有说过`double`在`printf`中不需要'l`. (9认同)

AnT*_*AnT 14

正确的%lf格式printfdouble,就像你使用它一样.您的代码没有任何问题.

格式%lfprintf的C语言,它创造了格式说明之间肤浅的"不一致"旧的(预C99)版本是不支持doubleprintfscanf.表面上的不一致已在C99中修复.

因此,在现代C是非常有意义喜欢使用%lfdouble,printf%f%lf具有%f持续两printf%f.


Fré*_*idi 9

%Lf(注意是大写L)是格式说明长双打.

对于普通的doubles,要么%e,%E,%f,%g还是%G会做.