【问题标题】:printf giving wrong output [closed]printf给出错误的输出[关闭]
【发布时间】:2013-11-13 06:07:44
【问题描述】:
#include<stdio.h>
#define square(x) x*x

    void main()
    {
        int i;
        i = 8 / square(4);
        printf("%d %d", i, 8/square(4));
    }

输出:8 8

但是如果我写下面的代码:

#include<stdio.h>
#define square(x) x*x

    void main()
    {
        float i;
        i = 8 / square(4);
        printf("%f %f", i, 8/square(4));
    }

给出输出:8.000000 0.000000

为什么会这样???请解释

【问题讨论】:

  • 如果您指定了%f,则使用浮点字面量。 8.0f/square(4.0f).
  • 总是尝试使用带有必要括号的宏来让生活更轻松!
  • int main()... 运算符优先级... 格式说明符错误... 您是否费心阅读基本的 C 教程?
  • Preprosessor 宏与函数不同。他们做了一个 textual 替换。在编写或使用宏之前了解其含义至关重要。

标签: c macros printf


【解决方案1】:

问题不仅在于格式说明符,还在于您定义宏的方式。应该是:

#define square(x) ((x)*(x))

宏也不是类型安全的。现在,如果您转换结果,您将看到发生了什么,因为 4 的平方是 16,而 8/16 是 0.5,它会被截断为 int,因此变为 0。对于正确的值,您应该这样进行类型转换:

printf("%d %d", (int)i, (int)(8/square(4)));
printf("\n%f %f", (float)i, (float)8/((float)square(4)));

Sample Output:

0 0
0.000000 0.500000

【讨论】:

    【解决方案2】:

    首先纠正这个:

    #define square(x) x*x
    

    #define square(x) ((x)*(x))
    

    宏替换后的正确结果。

    现在,在您的第一个程序中,正如其他人解释的那样,您使用错误的格式说明符 %f 来打印整数(8/(square(4) 将计算为整数),这是未定义的行为。

    在第二个程序中,8/square(4) 类型提升为float,因为您将结果存储在float i 中。因此,您在第一次打印时会得到8.000000。在第二次打印时,由于与上述相同的原因,结果错误。

    【讨论】:

    • 我没有看到第一个程序使用%f 作为格式说明符的证据。不过,如果有,您的分析将是准确的。
    【解决方案3】:

    第一个很容易理解,所以我只关注第二个。您将 %f 用于需要浮点数的第二个参数,而 C 编译器将 8/square(4) 作为整数。这种不匹配会破坏您的结果。

    【讨论】:

      【解决方案4】:

      8/square(4) 结果为int 并尝试使用%f 打印整数是Undefined behavior。所以调试你在第二种情况下得到的值是没有用的。

      如果您使用的是 gcc 编译器,那么命令 cc -E filename.c 可能会澄清您的疑问。

      【讨论】:

        【解决方案5】:

        这是因为您在第二个程序中将 float 作为数据类型。

        8/square(4) 将给出一个整数结果,因此您的输出会出错。你用 %f 打印一个整数。

        就是这么简单……

        【讨论】:

          【解决方案6】:

          因为 %f 表示数字的类型是双精度,默认精度

          【讨论】:

            猜你喜欢
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 2016-05-05
            • 1970-01-01
            • 2020-08-15
            • 1970-01-01
            • 1970-01-01
            • 2014-05-29
            相关资源
            最近更新 更多