tmp/tmpzp_flrq1/{from.md → to.md}
RENAMED
|
@@ -1,29 +1,38 @@
|
|
| 1 |
## Structured binding declarations <a id="dcl.struct.bind">[[dcl.struct.bind]]</a>
|
| 2 |
|
| 3 |
-
A structured binding declaration introduces the *identifier*s `v
|
| 4 |
-
`v
|
| 5 |
-
[[basic.scope.declarative]]
|
| 6 |
-
|
| 7 |
-
|
|
|
|
|
|
|
| 8 |
*assignment-expression* in the *initializer* has array type `A` and no
|
| 9 |
-
*ref-qualifier* is present, `e`
|
| 10 |
-
copy-initialized or direct-initialized from the corresponding element of
|
| 11 |
-
the *assignment-expression* as specified by the form of the
|
| 12 |
-
*initializer*. Otherwise, `e` is defined as-if by
|
| 13 |
|
| 14 |
``` bnf
|
| 15 |
-
attribute-specifier-seqₒₚₜ
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 16 |
```
|
| 17 |
|
| 18 |
where the declaration is never interpreted as a function declaration and
|
| 19 |
the parts of the declaration other than the *declarator-id* are taken
|
| 20 |
from the corresponding structured binding declaration. The type of the
|
| 21 |
-
*id-expression* `e` is called `E`.
|
| 22 |
|
| 23 |
-
[*Note 1*: `E` is never a reference type
|
| 24 |
-
|
|
|
|
|
|
|
| 25 |
|
| 26 |
If `E` is an array type with element type `T`, the number of elements in
|
| 27 |
the *identifier-list* shall be equal to the number of elements of `E`.
|
| 28 |
Each `v`ᵢ is the name of an lvalue that refers to the element i of the
|
| 29 |
array and whose type is `T`; the referenced type is `T`.
|
|
@@ -39,38 +48,49 @@ array and whose type is `T`; the referenced type is `T`.
|
|
| 39 |
```
|
| 40 |
|
| 41 |
— *end example*]
|
| 42 |
|
| 43 |
Otherwise, if the *qualified-id* `std::tuple_size<E>` names a complete
|
| 44 |
-
type
|
| 45 |
-
|
| 46 |
-
|
| 47 |
-
|
| 48 |
-
|
| 49 |
-
|
| 50 |
-
|
| 51 |
-
|
| 52 |
-
|
|
|
|
|
|
|
|
|
|
| 53 |
|
| 54 |
-
[*Note 3*: Ordinary unqualified lookup
|
| 55 |
-
|
| 56 |
|
| 57 |
-
In either case, `e` is an lvalue if the type of the entity `e` is an
|
| 58 |
lvalue reference and an xvalue otherwise. Given the type `Tᵢ` designated
|
| 59 |
-
by `std::tuple_element<i, E>::type`
|
| 60 |
-
|
| 61 |
-
|
| 62 |
-
|
| 63 |
|
| 64 |
-
|
| 65 |
-
|
| 66 |
-
|
| 67 |
-
|
| 68 |
-
|
| 69 |
-
|
| 70 |
-
|
| 71 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 72 |
cv `Tᵢ`. The lvalue is a bit-field if that member is a bit-field.
|
| 73 |
|
| 74 |
[*Example 2*:
|
| 75 |
|
| 76 |
``` cpp
|
|
|
|
| 1 |
## Structured binding declarations <a id="dcl.struct.bind">[[dcl.struct.bind]]</a>
|
| 2 |
|
| 3 |
+
A structured binding declaration introduces the *identifier*s `v₀`,
|
| 4 |
+
`v₁`, `v₂`, … of the *identifier-list* as names
|
| 5 |
+
[[basic.scope.declarative]] of *structured binding*s. Let cv denote the
|
| 6 |
+
*cv-qualifier*s in the *decl-specifier-seq* and *S* consist of the
|
| 7 |
+
*storage-class-specifier*s of the *decl-specifier-seq* (if any). A cv
|
| 8 |
+
that includes `volatile` is deprecated; see [[depr.volatile.type]].
|
| 9 |
+
First, a variable with a unique name *`e`* is introduced. If the
|
| 10 |
*assignment-expression* in the *initializer* has array type `A` and no
|
| 11 |
+
*ref-qualifier* is present, *`e`* is defined by
|
|
|
|
|
|
|
|
|
|
| 12 |
|
| 13 |
``` bnf
|
| 14 |
+
attribute-specifier-seqₒₚₜ *S* cv 'A' e ';'
|
| 15 |
+
```
|
| 16 |
+
|
| 17 |
+
and each element is copy-initialized or direct-initialized from the
|
| 18 |
+
corresponding element of the *assignment-expression* as specified by the
|
| 19 |
+
form of the *initializer*. Otherwise, *`e`* is defined as-if by
|
| 20 |
+
|
| 21 |
+
``` bnf
|
| 22 |
+
attribute-specifier-seqₒₚₜ decl-specifier-seq ref-qualifierₒₚₜ e initializer ';'
|
| 23 |
```
|
| 24 |
|
| 25 |
where the declaration is never interpreted as a function declaration and
|
| 26 |
the parts of the declaration other than the *declarator-id* are taken
|
| 27 |
from the corresponding structured binding declaration. The type of the
|
| 28 |
+
*id-expression* *`e`* is called `E`.
|
| 29 |
|
| 30 |
+
[*Note 1*: `E` is never a reference type [[expr.prop]]. — *end note*]
|
| 31 |
+
|
| 32 |
+
If the *initializer* refers to one of the names introduced by the
|
| 33 |
+
structured binding declaration, the program is ill-formed.
|
| 34 |
|
| 35 |
If `E` is an array type with element type `T`, the number of elements in
|
| 36 |
the *identifier-list* shall be equal to the number of elements of `E`.
|
| 37 |
Each `v`ᵢ is the name of an lvalue that refers to the element i of the
|
| 38 |
array and whose type is `T`; the referenced type is `T`.
|
|
|
|
| 48 |
```
|
| 49 |
|
| 50 |
— *end example*]
|
| 51 |
|
| 52 |
Otherwise, if the *qualified-id* `std::tuple_size<E>` names a complete
|
| 53 |
+
class type with a member named `value`, the expression
|
| 54 |
+
`std::tuple_size<E>::value` shall be a well-formed integral constant
|
| 55 |
+
expression and the number of elements in the *identifier-list* shall be
|
| 56 |
+
equal to the value of that expression. Let `i` be an index prvalue of
|
| 57 |
+
type `std::size_t` corresponding to `v`_`i`. The *unqualified-id* `get`
|
| 58 |
+
is looked up in the scope of `E` by class member access lookup
|
| 59 |
+
[[basic.lookup.classref]], and if that finds at least one declaration
|
| 60 |
+
that is a function template whose first template parameter is a non-type
|
| 61 |
+
parameter, the initializer is `e.get<i>()`. Otherwise, the initializer
|
| 62 |
+
is `get<i>(e)`, where `get` is looked up in the associated namespaces
|
| 63 |
+
[[basic.lookup.argdep]]. In either case, `get<i>` is interpreted as a
|
| 64 |
+
*template-id*.
|
| 65 |
|
| 66 |
+
[*Note 3*: Ordinary unqualified lookup [[basic.lookup.unqual]] is not
|
| 67 |
+
performed. — *end note*]
|
| 68 |
|
| 69 |
+
In either case, *`e`* is an lvalue if the type of the entity *`e`* is an
|
| 70 |
lvalue reference and an xvalue otherwise. Given the type `Tᵢ` designated
|
| 71 |
+
by `std::tuple_element<i, E>::type` and the type `Uᵢ` designated by
|
| 72 |
+
either `Tᵢ&` or `Tᵢ&&`, where `Uᵢ` is an lvalue reference if the
|
| 73 |
+
initializer is an lvalue and an rvalue reference otherwise, variables
|
| 74 |
+
are introduced with unique names `rᵢ` as follows:
|
| 75 |
|
| 76 |
+
``` bnf
|
| 77 |
+
*S* 'Uᵢ rᵢ =' initializer ';'
|
| 78 |
+
```
|
| 79 |
+
|
| 80 |
+
Each `vᵢ` is the name of an lvalue of type `Tᵢ` that refers to the
|
| 81 |
+
object bound to `rᵢ`; the referenced type is `Tᵢ`.
|
| 82 |
+
|
| 83 |
+
Otherwise, all of `E`’s non-static data members shall be direct members
|
| 84 |
+
of `E` or of the same base class of `E`, well-formed when named as
|
| 85 |
+
`e.name` in the context of the structured binding, `E` shall not have an
|
| 86 |
+
anonymous union member, and the number of elements in the
|
| 87 |
+
*identifier-list* shall be equal to the number of non-static data
|
| 88 |
+
members of `E`. Designating the non-static data members of `E` as `m₀`,
|
| 89 |
+
`m₁`, `m₂`, … (in declaration order), each `v`ᵢ is the name of an lvalue
|
| 90 |
+
that refers to the member `m`ᵢ of *`e`* and whose type is cv `Tᵢ`, where
|
| 91 |
+
`Tᵢ` is the declared type of that member; the referenced type is
|
| 92 |
cv `Tᵢ`. The lvalue is a bit-field if that member is a bit-field.
|
| 93 |
|
| 94 |
[*Example 2*:
|
| 95 |
|
| 96 |
``` cpp
|