简体   繁体   English

*&++我在C ++ 03中导致未定义的行为吗?

[英]Does *&++i cause undefined behaviour in C++03?

In another answer it was stated that prior to C++11, where i is an int , then use of the expression: 另一个答案中 ,有人说在C ++ 11之前, i是一个int ,然后使用表达式:

*&++i

caused undefined behaviour. 导致未定义的行为。 Is this true? 这是真的?

On the other answer there was a little discussion in comments but it seems unconvincing. 另一个答案是在评论中进行了一些讨论,但似乎并不令人信服。

It makes little sense to ask whether *&++i in itself has UB. 询问*&++i本身是否具有UB是没有意义的。 The deferencing doesn't necessarily access the stored value (prior or new) of i , as you can see by using this as an initializer expression for a reference. 引用不一定访问i的存储值(先前或新的),正如您可以通过将其用作引用的初始化表达式所看到的那样。 Only if an rvalue conversion is involved (usage in such context) is there any question to discuss at all. 只有涉及右值转换(在这种情况下使用)才有任何问题需要讨论。 And then, since we can use the value of ++i , we can use the value of *&++i with exactly the same caveats as for ++i . 然后,因为我们可以利用的价值++i ,我们可以利用的价值*&++i一模一样的警告作为++i

The original question concerned essentially i = ++i , which is the same as i = *&++i . 最初的问题主要涉及i = ++i ,这与i = *&++i That was undefined behavior in C++03, due to i being modified twice between sequence points, and is well-defined in C++11, due to the side-effects of the assignment operator being sequenced after the value computations of the left and right hand sides. 这是C ++ 03中未定义的行为,因为i在序列点之间被修改了两次,并且在C ++ 11中被很好地定义,因为在左边的值计算之后赋值运算符被排序的副作用和右手边。

It is perhaps relevant to note that the non-normative examples in the C++98 and C++03 standards, were incorrect, describing some cases of formally Undefined Behavior as merely unspecified behavior. 或许有必要指出,C ++ 98和C ++ 03标准中的非规范性示例是不正确的,将正式未定义行为的某些情况描述为仅仅未指定的行为。 Thus, the intent has not been entirely clear, all the way back. 因此,意图一直没有完全清楚。 A good rule of thumb is to simply not rely on such obscure corner cases of the language, to avoid them: one should not need to be a language lawyer in order to make sense of the code… 一个好的经验法则是不要依赖语言的这些模糊的角落案例,以避免它们:为了理解代码,不应该成为一名语言律师......

I think the question only makes sense if we deal with the expression: 我认为这个问题只有在我们处理表达式时才有意义:

i = *&++i;

The relevant quote in the C++03 standard would be [expr]/4: C ++ 03标准中的相关引用将是[expr] / 4:

Except where noted, the order of evaluation of operands of individual operators and subexpressions of individual expressions, and the order in which side effects take place, is unspecified. 除非另有说明,否则单个运算符的操作数和单个表达式的子表达式的评估顺序以及副作用发生的顺序是未指定的。 Between the previous and next sequence point a scalar object shall have its stored value modified at most once by the evaluation of an expression. 在前一个和下一个序列点之间,标量对象应通过表达式的计算最多修改其存储值一次。 Furthermore, the prior value shall be accessed only to determine the value to be stored. 此外,只能访问先前值以确定要存储的值。 The requirements of this paragraph shall be met for each allowable ordering of the subexpressions of a full expression; 对于完整表达式的子表达式的每个允许排序,应满足本段的要求; otherwise the behavior is undefined. 否则行为未定义。

 i = ++i + 1; // the behavior is unspecified 

We can just compare the sequencing of i = *&++i vs i = ++i + 1 to determine that the same rule causes both to be unspecified. 我们可以比较i = *&++ii = ++i + 1的排序,以确定相同的规则导致两者都未指定。 They are both statements of the form: 它们都是以下形式的陈述:

i = f(++i);

For any function f , the reading of i on the left-hand side and the side-effect of the ++i on the right-hand side are not sequenced relative with each other. 对于任何函数f ,左侧的i的读数和右侧的++i的副作用不相对于彼此排序。 Hence, undefined behavior. 因此,未定义的行为。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM