我试图使用指针迭代对象数组。一次打印一个值似乎工作正常,但当我尝试将它们全部打印在一起时,它会以相反的顺序给出结果。
#include<iostream>
using namespace std;
class car{
int tires;
public:
car(int a) {tires = a;};
int GetTires(){return tires;};
};
int main() {
car array[4] = { 2, 4, 6, 8 };
car *p;
p = array;
cout << ((p++)->GetTires()) << " " << ((p++)->GetTires()) << " " << ((p++)->GetTires()) << " " << ((p++)->GetTires()) << endl;
//Prints: 8 6 4 2
p = array;
cout << ((p++)->GetTires()) << " ";
cout << ((p++)->GetTires()) << " ";
cout << ((p++)->GetTires()) << " ";
cout << ((p++)->GetTires()) << " " << endl;
//Prints: 2 4 6 8
return 0;
}
使用C函数&#39; printf&#39;也提供相同的输出。任何人都可以解释为什么会这样吗? TIA。
答案 0 :(得分:8)
如果您使用的是早于C ++ 17的编译器,那么(p++)->GetTires()
中std::cout::operator <<
评估的顺序是未定义的。因此您的代码会产生未定义的行为。由于另一个评估顺序,另一个编译器或带有其他编译器设置的编译器可能会产生另一个输出。
在前一个和下一个序列点之间,必须访问由表达式求值修改的标量对象的先前值,以确定要存储的值。如果以任何其他方式访问它,则行为未定义。
cout << i << i++; // undefined behavior (until C++17) a[i] = i++; // undefined behavior (until C++17)
建议阅读:What are the evaluation order guarantees introduced by C++17?
答案 1 :(得分:1)
代码
cout << ((p++)->GetTires()) << " " << ((p++)->GetTires()) << " " << ((p++)->GetTires()) << " " << ((p++)->GetTires()) << endl;
与
不一样 cout << ((p++)->GetTires()) << " ";
cout << ((p++)->GetTires()) << " ";
cout << ((p++)->GetTires()) << " ";
cout << ((p++)->GetTires()) << " " << endl;
这是典型的运营商&lt;&lt;长相
ostream& operator<<(ostream& os, const Type& dt)
{
os << dt.value;
return os;
}
第一行中发生的是编译器将评估包含增量运算符的所有子表达式。评估顺序不是由标准定义的,但可能不是执行方向。在结果中,首先评估最后一个子表达式,并将增量转移到第三个表达式,依此类推。