The simple-type-specifier auto is a placeholder for a type to be deduced ([dcl.spec.auto]). A type-specifier of the form typenameopt nested-name-specifieropt template-name is a placeholder for a deduced class type ([dcl.type.class.deduct]). The template-name shall name a class template that is not an injected-class-name. The other simple-type-specifiers specify either a previously-declared type, a type determined from an expression, or one of the fundamental types. Table 11 summarizes the valid combinations of simple-type-specifiers and the types they specify.
Table
11—
simple-type-specifiersand the types they specify
When multiple simple-type-specifiers are allowed, they can be freely intermixed with other decl-specifiers in any order. [ Note: It is implementation-defined whether objects of char type are represented as signed or unsigned quantities. The signed specifier forces char objects to be signed; it is redundant in other contexts. — end note ]
For an expression e, the type denoted by decltype(e) is defined as follows:
if e is an unparenthesized id-expression naming a structured binding ([dcl.struct.bind]), decltype(e) is the referenced type as given in the specification of the structured binding declaration;
otherwise, if e is an unparenthesized id-expression or an unparenthesized class member access, decltype(e) is the type of the entity named by e. If there is no such entity, or if e names a set of overloaded functions, the program is ill-formed;
otherwise, if e is an xvalue, decltype(e) is T&&, where T is the type of e;
otherwise, if e is an lvalue, decltype(e) is T&, where T is the type of e;
otherwise, decltype(e) is the type of e.
The operand of the decltype specifier is an unevaluated operand.
[ Example:
const int&& foo(); int i; struct A { double x; }; const A* a = new A(); decltype(foo()) x1 = 17; decltype(i) x2; decltype(a->x) x3; decltype((a->x)) x4 = x3;
— end example ] [ Note: The rules for determining types involving decltype(auto) are specified in [dcl.spec.auto]. — end note ]
If the operand of a decltype-specifier is a prvalue, the temporary materialization conversion is not applied and no result object is provided for the prvalue. The type of the prvalue may be incomplete. [ Note: As a result, storage is not allocated for the prvalue and it is not destroyed. Thus, a class type is not instantiated as a result of being the type of a function call in this context. In this context, the common purpose of writing the expression is merely to refer to its type. In that sense, a decltype-specifier is analogous to a use of a typedef-name, so the usual reasons for requiring a complete type do not apply. In particular, it is not necessary to allocate storage for a temporary object or to enforce the semantic constraints associated with invoking the type's destructor. — end note ] [ Note: Unlike the preceding rule, parentheses have no special meaning in this context. — end note ] [ Example:
template<class T> struct A { ~A() = delete; }; template<class T> auto h() -> A<T>; template<class T> auto i(T) -> T; template<class T> auto f(T) -> decltype(i(h<T>())); template<class T> auto f(T) -> void; auto g() -> void { f(42); } template<class T> auto q(T) -> decltype((h<T>())); void r() { q(42); }
— end example ]
RetroSearch is an open source project built by @garambo | Open a GitHub Issue
Search and Browse the WWW like it's 1997 | Search results from DuckDuckGo
HTML:
3.2
| Encoding:
UTF-8
| Version:
0.7.4