我有以下代码:
int f(int &x, int c){
c = c - 1;
if (c == 0) return 1;
x = x + 1;
return f(x, c)*x;
}
现在,假设我这样调用上面的函数:
int p = 5;
std::cout << f(p, p) << std::endl;
输出是9^4
,因为x
是通过引用传递的,所以x
的最终值应该是9,但是当上述函数的return
语句改为:
return x*f(x, c);
输出为 3024 (6*7*8*9)
。为什么输出有差异?它与 Operator*
的评估顺序有什么关系吗?如果我们被要求预测上面这段代码的输出,它是固定的、编译器相关的还是未指定的?
最佳答案
当你写的时候:
f(x,c)*x
编译器可以选择在调用 f
之前或之后检索 x
中存储的值(对于第二个操作数)。因此,有许多可能的执行方式。编译器不必在此选择中使用任何一致性。
为了避免这个问题你可以这样写:
auto x_temp = x;
return f(x, c) * x_temp;
注意:这是未指定的行为;不是未定义的行为,因为在任何函数调用之前和之后都有一个序列点(或者在 C++11 术语中,函数内的语句相对于调用代码是不确定排序的,而不是未排序的)。
关于c++ - 运算符(operator)的评价顺序 *,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42082041/