在整数和浮点数上打印操作结果

时间:2017-08-29 11:33:47

标签: c

考虑以下C程序:

int main() {
    int a =2;
    float b = 2;
    float c = 3;
    int d = 3;
    printf("%d %f %d %f %d %f %d %f\n", a/c, a/c, a/d, a/d, b/c, b/c, b/d, b/d);
    printf("%d\n", a/c);
}

这个输出是:

 0 0.666667 0 0.666667 2 0.666667 0 0.666667
 539648

我根本无法理解这一点。为什么打印a / c为整数给出0,而b / c给出2? Aren的所有整数在涉及浮点数和整数的计算中被提升为浮点数?所以两种情况下答案都应为0。

在输出的第二行中,我只是将一个/ c打印为一个整数,由于某种原因它给出了一个垃圾值(即使它在第一个复合printf语句中打印时它给出了0)。为什么会这样?

2 个答案:

答案 0 :(得分:6)

您有未定义的行为:

printf("%d %f %d %f %d %f %d %f\n", a/c, a/c, a/d, a/d, b/c, b/c, b/d, b/d);

printf的格式说明符必须与提供的参数的类型匹配。由于printf没有提供带有类型的参数列表,但只有...除标准类型转换外没有隐式类型转换。

如果你有UB,基本上什么都可以发生。

可能发生的事情如下:

根据格式说明符,printf会从调用参数中消耗一定数量的字节。此字节数与指定的格式类型匹配。如果字节数与作为参数传递的字节数不匹配,则所有后续参数都不同步。 当然,您对数据的解释不正确。

答案 1 :(得分:1)

对于根据C标准的初学者,不带参数的函数main应声明为

int main( void )

如果您有以下声明

int a =2;
float c = 3;

然后按以下方式调用函数printf

printf( "%d", a / c );

然后在引擎盖后面发生以下事件。

由于通常的算术转换,表达式a / c的类型为float

当使用省略号表示法声明函数printf然后使用类型a / c的表达式float时,应用转换的默认参数促销表达式double

作为此调用的结果,尝试使用为double类型设计的转换说明符%d输出类型int的表达式。 Hanse呼叫有不确定的行为。

来自C标准(7.21.6.1 fprintf函数)

  

9如果转换规范无效,则行为为   undefined .275)如果任何参数不是正确的类型   相应的转换规范,行为未定义。

相关问题