This is an unofficial snapshot of the ISO/IEC JTC1 SC22 WG21 Core Issues List revision 115d. See http://www.open-std.org/jtc1/sc22/wg21/ for the official list.
2024-10-26
(From submission #536.)
For T{...}, the rule in 7.6.1.4 [expr.type.conv] paragraph 2 yields a prvalue of reference type if T is a reference type:
... Otherwise, the expression is a prvalue of the specified type whose result object is direct-initialized (9.4) with the initializer. ...
Also, it should be clarified that void(1, 2) and void{1} are ill-formed.
Possible resolution [SUPERSEDED]:
Change in 7.6.1.4 [expr.type.conv] paragraph 1 and 2 as follows:
A simple-type-specifier (9.2.9.3 [dcl.type.simple]) or typename-specifier (13.8 [temp.res]) followed by a parenthesized optional expression-list or by a braced-init-list (the initializer) constructs a value of the specified type given the initializer. If the type is a placeholder for a deduced class type, it is replaced by the return type of the function selected by overload resolution for class template deduction (12.2.2.9 [over.match.class.deduct]) for the remainder of this subclause. Otherwise, if the type contains a placeholder type, it is replaced by the type determined by placeholder type deduction (9.2.9.7.2 [dcl.type.auto.deduct]). Let T denote the resulting type. [ Example: ... ]
If the initializer is a parenthesized single expression, the type conversion expression is equivalent to the corresponding cast expression (7.6.3 [expr.cast]). Otherwise, if
the typeT is cv voidand, the initializerisshall be () or {} (after pack expansion, if any), and the expression is a prvalue of type void that performs no initialization. Otherwise, the expressionis a prvalue of the specified type whose result object is direct-initialized (9.4 [dcl.init]) with the initializerhas the same effect as direct-initializing an invented variable t of type T from the initializer and then using t as the result of the expression. The result is an lvalue if T is an lvalue reference type or an rvalue reference to function type, an xvalue if T is an rvalue reference to object type, and a prvalue otherwise. If the initializer is a parenthesized optional expression-list,the specified typeT shall not be an array type.
CWG 2024-06-14
The resolution above introduces an additional variable even for a prvalue, which defeats mandatory copy elision. Use the pattern from 7.6.1.9 [expr.static.cast] paragraph 4 instead.
Proposed resolution (approved by CWG 2024-10-25):
Change in 7.6.1.4 [expr.type.conv] paragraph 1 and 2 as follows, move the example to the bottom, and add bullets:
A simple-type-specifier (9.2.9.3 [dcl.type.simple]) or typename-specifier (13.8 [temp.res]) followed by a parenthesized optional expression-list or by a braced-init-list (the initializer) constructs a value of the specified type given the initializer. If the type is a placeholder for a deduced class type, it is replaced by the return type of the function selected by overload resolution for class template deduction (12.2.2.9 [over.match.class.deduct]) for the remainder of this subclause. Otherwise, if the type contains a placeholder type, it is replaced by the type determined by placeholder type deduction (9.2.9.7.2 [dcl.type.auto.deduct]). Let T denote the resulting type.
[ Example: ... ]Then:
If the initializer is a parenthesized optional expression-list,
- If the initializer is a parenthesized single expression, the type conversion expression is equivalent to the corresponding cast expression (7.6.3 [expr.cast]).
- Otherwise, if
the typeT is cv voidand, the initializerisshall be () or {} (after pack expansion, if any), and the expression is a prvalue of type void that performs no initialization.- Otherwise, if T is a reference type, the expression has the same effect as direct-initializing an invented variable t of type T from the initializer and then using t as the result of the expression; the result is an lvalue if T is an lvalue reference type or an rvalue reference to function type and an xvalue otherwise.
- Otherwise, the expression is a prvalue of
the specifiedtype T whose result object is direct-initialized (9.4 [dcl.init]) with the initializer.the specified typeT shall not be an array type.[Example: ... ]