我的老师向我提供了此代码,它返回 31,40 ,但我无法弄明白为什么。它返回它的原因是什么原因?
void main() {
int *ptr;
int arr[5] = { 10, 20, 30, 40, 50 };
ptr = &arr[3];
cout << ++*ptr-- << ", " << *ptr;
}
答案 0 :(得分:5)
cout << ++*ptr-- << ", " << *ptr;
是
operator <<(cout.operator <<(++*ptr--), ", ").operator <<(*ptr);
问题可以简化为:
f(f(ptr--), ptr)
而f(ptr--)
和ptr
之间的评估顺序未指定(在ptr--
和ptr
之间更为具体)。
所以你得到了给定代码的未定义行为。
答案 1 :(得分:3)
C ++标准陈述
第1.9 / 15节[intro.execution] :除非另有说明,否则对各个运算符的操作数和个别子表达式的操作数进行评估 表达式没有排序。 (...)如果对标量物体的副作用相对于另一个副作用而言是无效的 相同的标量对象或使用相同值的值计算 标量对象,行为未定义。
++*ptr--
和*ptr
是使用相同对象的同一表达式的未序列子表达式:没有任何保证它们从左到右进行求值。因此,根据标准,这会导致未定义的行为。您的结果往往表明您的编译器选择先评估*ptr
然后评估++*ptr--
。
修改: ++*ptr--
为++(*ptr--))
。这里,运算符++
的操作数也使用ptr
副作用的对象--
。所以这也是未定义的行为。看起来在您的情况下,编译器首先评估*ptr--
,其导致40和递减的ptr
,然后在解除引用的递减指针上应用++
(即30递增1)。