在 C 中使用格式说明符打印

Printing with format specifiers in C

在 class 测验中,我被要求编写以下代码片段的输出。

x = 1.234;
printf("x=%2d");

变量 x 包含点值,所以我假设它是 float/double 类型。

在论文中我回答说这段代码只是简单地在引号内打印语句(如 x=%2d),因为在打印函数中它会按原样打印 " " 中的任何内容。

但后来我 运行 我的编译器中的代码找到了 x=4199232 的输出(虽然不同的编译器的数量不同) (编辑-我在这里添加了编译代码)

#include <stdio.h>

int main() {
    float x = 1.234;
    printf("x=%2d");
    return 0;
}

任何人都可以向我解释这里到底发生了什么。

该代码具有未定义的行为(这解释了为什么 不同编译器中的数字不同 ),因为您没有为转换提供 int 类型的参数 %2d.

如果你写了这个:

x = 1.234;
printf("x=%2d", x);

输出将取决于 x 的类型,它没有出现在代码片段中。如果 x 定义为类型 int 或更小的整数类型,包括 _Bool,则输出应为 x= 1,但如果 x 具有任何其他算术类型,包括 floatdouble,行为再次未定义,因为参数不具有 %d.

的预期类型

另请注意,格式字符串中没有尾随 \n,因此输出可能会延迟到程序结束,并且可能根本不会出现在某些不一致的系统上。

在您的示例代码中,由于缺少 printf 的参数,行为未定义,但您确实将 x 定义为 float,这将被隐式转换为double 传递给 printf 时,对 %d 无效。

这是修改后的版本:

#include <stdio.h>

int main() {
    double x = 1.234;            // only use `float` when necessary
    printf("x=%2d\n", (int)x);   // outputs `x= 1`
    printf("x=%2f\n", x);        // outputs `x=1.234000`
    printf("x=%2g\n", x);        // outputs `x=1.234`
    printf("x=%.2f\n", x);       // outputs `x=1.23`
    return 0;
}

在此声明中

printf("x=%2d");

您忘记为转换说明符指定参数 d。所以程序将尝试输出存储在内存中第二个参数应该是的任何内容。

所以程序有未定义的行为。

如果你指定第二个参数,它也会有未定义的行为

printf("x=%2d", x );

因为对 float 类型的对象使用了无效的转换说明符。

只输出你应该写的格式字符串

printf("x=%%2d");