为什么 cout<<++i + ar[++i];和 cout<<ar[++i]+ ++i;给出不同的输出?
Why cout<<++i + ar[++i]; and cout<<ar[++i]+ ++i; give different output?
我已阅读有关未定义行为的内容。
说 a[i] = a[i++]
导致未定义的行为。
但是我不明白为什么
的输出
int arr[10] = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 };
int i = 0;
cout << arr[++i] + ++i << " " << i;
是3 2
和
的输出
int arr[10] = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 };
int i = 0;
cout << ++i + arr[++i] << " " << i;
是4 2
首先 - a[i] = a[i++]
自 C++17 以来定义明确。在该标准修订版中,顺序规则大大收紧,赋值运算符右侧的求值 顺序在 左侧的求值之前,这意味着所有右侧的副作用必须在左侧的评估开始之前完成。
所以该代码等同于a[i+1] = a[i]; ++i;
自 C++17 起,<<
运算符也具有左右排序,即左操作数在右操作数之前排序。
现在,++i
定义为 i+=1
,并且与上述类似的考虑适用于复合赋值运算符的计算。我们可以说 ++i
是“原子地”发生的。
但是,+
运算符仍然是 未排序的 ,这是由 [intro.execution]/17:
定义的
Except where noted, evaluations of operands of individual operators and of subexpressions of individual expressions are unsequenced.
[...]
If a side effect on a memory location is unsequenced relative to either another side effect on the same memory location or a value computation using the value of any object in the same memory location, and they are not
potentially concurrent, the behavior is undefined
不幸的是,这意味着 ++i + a[++i]
的行为仍然未定义,因为 +
的左操作数修改 i
,而 +
的右操作数修改 i
,并且这些操作数计算相对于彼此是无序的。
之前有人提议让 +
和类似的运算符也按左右顺序排列,但显然这还没有被标准接受。
我已阅读有关未定义行为的内容。
a[i] = a[i++]
导致未定义的行为。
但是我不明白为什么
的输出int arr[10] = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 };
int i = 0;
cout << arr[++i] + ++i << " " << i;
是3 2
和
的输出int arr[10] = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 };
int i = 0;
cout << ++i + arr[++i] << " " << i;
是4 2
首先 - a[i] = a[i++]
自 C++17 以来定义明确。在该标准修订版中,顺序规则大大收紧,赋值运算符右侧的求值 顺序在 左侧的求值之前,这意味着所有右侧的副作用必须在左侧的评估开始之前完成。
所以该代码等同于a[i+1] = a[i]; ++i;
自 C++17 起,<<
运算符也具有左右排序,即左操作数在右操作数之前排序。
现在,++i
定义为 i+=1
,并且与上述类似的考虑适用于复合赋值运算符的计算。我们可以说 ++i
是“原子地”发生的。
但是,+
运算符仍然是 未排序的 ,这是由 [intro.execution]/17:
Except where noted, evaluations of operands of individual operators and of subexpressions of individual expressions are unsequenced.
[...]
If a side effect on a memory location is unsequenced relative to either another side effect on the same memory location or a value computation using the value of any object in the same memory location, and they are not potentially concurrent, the behavior is undefined
不幸的是,这意味着 ++i + a[++i]
的行为仍然未定义,因为 +
的左操作数修改 i
,而 +
的右操作数修改 i
,并且这些操作数计算相对于彼此是无序的。
之前有人提议让 +
和类似的运算符也按左右顺序排列,但显然这还没有被标准接受。