C语言 printf 和 long double

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/4089174/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-02 06:54:34  来源:igfitidea点击:

printf and long double

cgccprintflong-double

提问by gameboy

I am using the latest gcc with Netbeans on Windows. Why doesn't long doublework? Is the printfspecifier %lfwrong?

我在 Windows 上使用带有 Netbeans 的最新 gcc。为什么不起作用long double?说明printf%lf错了吗?

Code:

代码:

#include <stdio.h>

int main(void)
{
    float aboat = 32000.0;
    double abet = 5.32e-5;
    long double dip = 5.32e-5;

    printf("%f can be written %e\n", aboat, aboat);
    printf("%f can be written %e\n", abet, abet);
    printf("%lf can be written %le\n", dip, dip);

    return 0;
}

Output:

输出:

32000.000000 can be written 3.200000e+004
0.000053 can be written 5.320000e-005
-1950228512509697500000000000000000000000000000000000000000000000000000000000000
000000000000000000000000000000000000000000000000000000000000000000000000.000000
can be written 2.725000e+002
Press [Enter] to close the terminal ...

采纳答案by AProgrammer

In addition to the wrong modifier, which port of gcc to Windows? mingw uses the Microsoft C library and I seem to remember that this library has no support for 80bits long double (microsoft C compiler use 64 bits long double for various reasons).

除了错误的修饰符,gcc的哪个端口到Windows?mingw 使用 Microsoft C 库,我似乎记得这个库不支持 80 位长双精度(微软 C 编译器出于各种原因使用 64 位长双精度)。

回答by nos

From the printf manpage:

从 printf 联机帮助页:

l (ell) A following integer conversion corresponds to a long int or unsigned long int argument, or a following n conversion corresponds to a pointer to a long int argument, or a following c conversion corresponds to a wint_t argument, or a following s conversion corresponds to a pointer to wchar_t argument.

l (ell) 后面的整数转换对应一个long int或unsigned long int参数,或者后面的n转换对应一个指向long int参数的指针,或者后面的c转换对应一个wint_t参数,或者后面的s转换对应于指向 wchar_t 参数的指针。

and

L A following a, A, e, E, f, F, g, or G conversion corresponds to a long double argument. (C99 allows %LF, but SUSv2 does not.)

a、A、e、E、f、F、g 或 G 转换后的 LA 对应于 long double 参数。(C99 允许 %LF,但 SUSv2 不允许。)

So, you want %Le, not %le

所以,你想要%Le,而不是%le

Edit: Some further investigation seems to indicate that Mingw uses the MSVC/win32 runtime(for stuff like printf) - which maps long double to double. So mixing a compiler (like gcc) that provides a native long double with a runtime that does not seems to .. be a mess.

编辑:一些进一步的调查似乎表明 Mingw 使用 MSVC/win32 运行时(对于 printf 之类的东西) - 它将 long double 映射到 double。因此,将提供本机 long double 的编译器(如 gcc)与似乎不会.. 的运行时混合在一起。

回答by Jerry Coffin

Yes -- for long double, you need to use %Lf(i.e., upper-case 'L').

是的 - 对于long double,您需要使用%Lf(即大写的“L”)。

回答by dnadlinger

If you are using MinGW, the problem is that by default, MinGW uses the I/O resp. formatting functions from the Microsoft C runtime, which doesn't support 80 bit floating point numbers (long double== doublein Microsoft land).

如果您使用的是 MinGW,问题是默认情况下,MinGW 使用 I/O 响应。来自 Microsoft C 运行时的格式化函数,它不支持 80 位浮点数(在 Microsoft 中是long double== double)。

However, MinGW also comes with a set of alternative implementations that doproperly support long doubles. To use them, prefix the function names with __mingw_(e.g. __mingw_printf). Depending on the nature of your project, you might also want to globally #define printf __mingw_printfor use -D__USE_MINGW_ANSI_STDIO(which enables the MinGW versions of all the printf-family functions).

然而,MinGW的还带有一组替代实现,正确地支持长一倍。要使用它们,请在函数名称前加上__mingw_(eg __mingw_printf)。根据您的项目的性质,您可能还希望全局#define printf __mingw_printf或使用-D__USE_MINGW_ANSI_STDIO(启用所有printf-family 功能的 MinGW 版本)。

回答by Jason Huntley

Was having this issue testing long doubles, and alas, I came across a fix! You have to compile your project with -D__USE_MINGW_ANSI_STDIO:

在测试长双打时遇到了这个问题,唉,我发现了一个修复程序!您必须使用 -D__USE_MINGW_ANSI_STDIO 编译您的项目:

Jason Huntley@centurian /home/developer/dependencies/Python-2.7.3/test $ gcc main.c

Jason Huntley@centurian /home/developer/dependencies/Python-2.7.3/test $ a.exe c=0.000000

Jason Huntley@centurian /home/developer/dependencies/Python-2.7.3/test $ gcc main.c -D__USE_MINGW_ANSI_STDIO

Jason Huntley@centurian /home/developer/dependencies/Python-2.7.3/test $ a.exe c=42.000000

Jason Huntley@centurian /home/developer/dependencies/Python-2.7.3/test $ gcc main.c

Jason Huntley@centurian /home/developer/dependencies/Python-2.7.3/test $ a.exe c=0.000000

Jason Huntley@centurian /home/developer/dependencies/Python-2.7.3/test $ gcc main.c -D__USE_MINGW_ANSI_STDIO

Jason Huntley@centurian /home/developer/dependencies/Python-2.7.3/test $ a.exe c=42.000000

Code:

代码:

Jason Huntley@centurian /home/developer/dependencies/Python-2.7.3/test
$ cat main.c
#include <stdio.h>

int main(int argc, char **argv)
{
   long double c=42;

   c/3;

   printf("c=%Lf\n",c);

   return 0;
}

回答by Jens Gustedt

In C99 the length modifier for long doubleseems to be Land not l. man fprintf(or equivalent for windows) should tell you for your particular platform.

在 C99 中,长度修饰符 forlong double似乎是L而不是lman fprintf(或 Windows 的等价物)应该告诉你你的特定平台。

回答by pmg

As has been said in other answers, the correct conversion specifier is "%Lf".

正如其他答案中所说,正确的转换说明符是"%Lf".

You might want to turn on the format warning by using -Wformat(or -Wall, which includes -Wformat) in the gcc invocation

您可能希望通过在 gcc 调用中使用-Wformat(或-Wall包含-Wformat)来打开格式警告

$ gcc source.c
$ gcc -Wall source.c
source.c: In function `main`:
source.c:5: warning: format "%lf" expects type `double`, but argument 2 has type `long double`
source.c:5: warning: format "%le" expects type `double`, but argument 3 has type `long double`
$

回答by Rupak Paul

printf and scanf function in C/C++ uses Microsoft C library and this library has no support for 10 byte long double. So when you are using printf and scanf function in your C/C++ code to print a long double as output and to take some input as a long double, it will always give you wrong result.

C/C++ 中的 printf 和 scanf 函数使用 Microsoft C 库,该库不支持 10 字节长双精度。因此,当您在 C/C++ 代码中使用 printf 和 scanf 函数打印 long double 作为输出并将某些输入作为 long double 时,它​​总是会给您错误的结果。

If you want to use long double then you have to use " __mingw_printf " and " __mingw_scanf " function instead of printf and scanf. It has support for 10 byte long double.

如果你想使用 long double 那么你必须使用“ __mingw_printf ”和“ __mingw_scanf ”函数而不是 printf 和 scanf 。它支持 10 字节长的 double。

Or you can define two macro like this : " #define printf __mingw_printf " and " #define scanf __mingw_scanf "

或者你可以像这样定义两个宏:“#define printf __mingw_printf”和“#define scanf __mingw_scanf”

Use standard format for long double : %Lf

对 long double 使用标准格式:%Lf