Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Can anyone explain this paragraph of the current C++0x standard draft?

Tags:

c++

c++11

Can anyone explain this statement from ISO N3242 §3.2, 2nd point

An expression is potentially evaluated unless it is an unevaluated operand (Clause 5) or a subexpression thereof. A variable or non-overloaded function whose name appears as a potentially-evaluated expression is odr-used unless it is an object that satisfies the requirements for appearing in a constant expression (5.19) and the lvalue-to-rvalue conversion (4.1) is immediately applied. this is odr-used if it appears as a potentiallyevaluated expression (including as the result of the implicit transformation in the body of a non-static member function (9.3.1)).

ISO Standard 2003 : says

An expression is potentially evaluated unless it appears where an integral constant expression is required (see 5.19), is the operand of the sizeof operator (5.3.3), or is the operand of the typeid operator and the expression does not designate an lvalue of polymorphic class type (5.2.8). An object or non-overloaded function is used if its name appears in a potentially-evaluated expression.

What is the actual difference in these statements?

Can any one explain this with the help of an example/program?

like image 563
1User Avatar asked Apr 06 '11 11:04

1User


1 Answers

"unevaluated operand" replaces "is the operand of the sizeof operator (5.3.3), or is the operand of the typeid operator and the expression does not designate an lvalue of polymorphic class type (5.2.8)". It has the same basic purpose, but doesn't try to list all the cases in the C++0x standard of operators whose operands aren't evaluated. decltype is a new one, for example.

"odr-used" replaces "used", I presume they figured that "used" alone might be ambiguous with other uses of the word "use" in the standard. In both cases, though, it's defining the sense of "used" which is relevant to the ODR.

So those aren't really changes, just re-wordings updated for C++0x.

This is a change:

A variable or non-overloaded function whose name appears as a potentially-evaluated expression is odr-used unless it is an object that satisfies the requirements for appearing in a constant expression (5.19) and the lvalue-to-rvalue conversion (4.1) is immediately
applied.

vs.

An object or non-overloaded function is used if its name appears in a potentially-evaluated
expression.

Suppose a is a static const int at global scope. Then in C++03 it is not used in the following statement:

char x[a];

because the context requires a constant expression. However, it is used in the following:

void foo(int); foo(a);

because the context doesn't require a constant expression.

In C++0x, a is not odr-used in either case. It's allowed to be in a constant expression, and in the function call, lvalue-rvalue conversion is immediately applied (because foo takes its parameter by value, not reference). So it qualifies for the "unless" which wasn't present in C++03.

There's also a difference in the definition of "potentially evaluated". In the first example, char x[a], a is potentially evaluated in C++03 but not in C++0x. I haven't checked whether anything else in the standard uses "potentially evaluated", that might be affected by this change. If it's only mentioned here then that part of it isn't a change, it's just that the exception has been moved from "potentially evaluated" to "used".

like image 62
Steve Jessop Avatar answered Oct 28 '22 06:10

Steve Jessop