From Jason Turner

[class.init]

Diff to HTML by rtfpessoa

Files changed (1) hide show
  1. tmp/tmpiwc2m_1s/{from.md → to.md} +71 -81
tmp/tmpiwc2m_1s/{from.md → to.md} RENAMED
@@ -1,7 +1,9 @@
1
  ## Initialization <a id="class.init">[[class.init]]</a>
2
 
 
 
3
  When no initializer is specified for an object of (possibly
4
  cv-qualified) class type (or array thereof), or the initializer has the
5
  form `()`, the object is initialized as specified in  [[dcl.init]].
6
 
7
  An object of class type (or array thereof) can be explicitly
@@ -61,11 +63,11 @@ complex v[6] = { 1, complex(1,2), complex(), 2 };
61
  ```
62
 
63
  Here, `complex::complex(double)` is called for the initialization of
64
  `v[0]` and `v[3]`, `complex::complex({}double, double)` is called for
65
  the initialization of `v[1]`, `complex::complex()` is called for the
66
- initialization `v[2]`, `v[4]`, and `v[5]`. For another example,
67
 
68
  ``` cpp
69
  struct X {
70
  int i;
71
  float f;
@@ -118,20 +120,18 @@ mem-initializer:
118
  mem-initializer-id:
119
  class-or-decltype
120
  identifier
121
  ```
122
 
123
- In a *mem-initializer-id* an initial unqualified *identifier* is looked
124
- up in the scope of the constructor’s class and, if not found in that
125
- scope, it is looked up in the scope containing the constructor’s
126
- definition.
127
 
128
  [*Note 1*: If the constructor’s class contains a member with the same
129
  name as a direct or virtual base class of the class, a
130
  *mem-initializer-id* naming the member or base class and composed of a
131
  single identifier refers to the class member. A *mem-initializer-id* for
132
- the hidden base class may be specified using a qualified
133
  name. — *end note*]
134
 
135
  Unless the *mem-initializer-id* names the constructor’s class, a
136
  non-static data member of the constructor’s class, or a direct or
137
  virtual base of that class, the *mem-initializer* is ill-formed.
@@ -150,11 +150,11 @@ C::C(): global_A() { } // mem-initializer for base A
150
  ```
151
 
152
  — *end example*]
153
 
154
  If a *mem-initializer-id* is ambiguous because it designates both a
155
- direct non-virtual base class and an inherited virtual base class, the
156
  *mem-initializer* is ill-formed.
157
 
158
  [*Example 2*:
159
 
160
  ``` cpp
@@ -238,14 +238,15 @@ struct A {
238
  };
239
  ```
240
 
241
  — *end example*]
242
 
243
- In a non-delegating constructor, if a given potentially constructed
244
- subobject is not designated by a *mem-initializer-id* (including the
245
- case where there is no *mem-initializer-list* because the constructor
246
- has no *ctor-initializer*), then
 
247
 
248
  - if the entity is a non-static data member that has a default member
249
  initializer [[class.mem]] and either
250
  - the constructor’s class is a union [[class.union]], and no other
251
  variant member of that union is designated by a *mem-initializer-id*
@@ -260,11 +261,11 @@ has no *ctor-initializer*), then
260
  [[class.union.anon]], no initialization is performed;
261
  - otherwise, the entity is default-initialized [[dcl.init]].
262
 
263
  [*Note 3*: An abstract class [[class.abstract]] is never a most derived
264
  class, thus its constructors never initialize virtual base classes,
265
- therefore the corresponding *mem-initializer*s may be
266
  omitted. — *end note*]
267
 
268
  An attempt to initialize more than one non-static data member of a union
269
  renders the program ill-formed.
270
 
@@ -286,14 +287,14 @@ struct B {
286
  B(int);
287
  };
288
 
289
  struct C {
290
  C() { } // initializes members as follows:
291
- A a; // OK: calls A::A()
292
  const B b; // error: B has no default constructor
293
- int i; // OK: i has indeterminate value
294
- int j = 5; // OK: j has the value 5
295
  };
296
  ```
297
 
298
  — *end example*]
299
 
@@ -399,13 +400,14 @@ B b(3); // use V()
399
  C c(4); // use V()
400
  ```
401
 
402
  — *end example*]
403
 
404
- Names in the *expression-list* or *braced-init-list* of a
405
- *mem-initializer* are evaluated in the scope of the constructor for
406
- which the *mem-initializer* is specified.
 
407
 
408
  [*Example 10*:
409
 
410
  ``` cpp
411
  class X {
@@ -424,15 +426,10 @@ of the constructor parameter `i`, initializes `X::i` with the value of
424
  the constructor parameter `i`, and initializes `X::j` with the value of
425
  `X::i`; this takes place each time an object of class `X` is created.
426
 
427
  — *end example*]
428
 
429
- [*Note 7*: Because the *mem-initializer* are evaluated in the scope of
430
- the constructor, the `this` pointer can be used in the *expression-list*
431
- of a *mem-initializer* to refer to the object being
432
- initialized. — *end note*]
433
-
434
  Member functions (including virtual member functions, [[class.virtual]])
435
  can be called for an object under construction. Similarly, an object
436
  under construction can be the operand of the `typeid` operator
437
  [[expr.typeid]] or of a `dynamic_cast` [[expr.dynamic.cast]]. However,
438
  if these operations are performed in a *ctor-initializer* (or in a
@@ -469,11 +466,11 @@ public:
469
  };
470
  ```
471
 
472
  — *end example*]
473
 
474
- [*Note 8*: [[class.cdtor]] describes the result of virtual function
475
  calls, `typeid` and `dynamic_cast`s during construction for the
476
  well-defined cases; that is, describes the polymorphic behavior of an
477
  object under construction. — *end note*]
478
 
479
  A *mem-initializer* followed by an ellipsis is a pack expansion
@@ -523,28 +520,28 @@ struct D1 : B1 {
523
  int x;
524
  int y = get();
525
  };
526
 
527
  void test() {
528
- D1 d(2, 3, 4); // OK: B1 is initialized by calling B1(2, 3, 4),
529
  // then d.x is default-initialized (no initialization is performed),
530
  // then d.y is initialized by calling get()
531
- D1 e; // error: D1 has a deleted default constructor
532
  }
533
 
534
  struct D2 : B2 {
535
  using B2::B2;
536
  B1 b;
537
  };
538
 
539
- D2 f(1.0); // error: B1 has a deleted default constructor
540
 
541
  struct W { W(int); };
542
  struct X : virtual W { using W::W; X() = delete; };
543
  struct Y : X { using X::X; };
544
  struct Z : Y, virtual W { using Y::Y; };
545
- Z z(0); // OK: initialization of Y does not invoke default constructor of X
546
 
547
  template<class T> struct Log : T {
548
  using T::T; // inherits all constructors from class T
549
  ~Log() { std::clog << "Destroying wrapper" << std::endl; }
550
  };
@@ -580,18 +577,18 @@ struct D2 : V1, V2 {
580
  using V1::V1;
581
  using V2::V2;
582
  };
583
 
584
  D1 d1(0); // error: ambiguous
585
- D2 d2(0); // OK: initializes virtual B base class, which initializes the A base class
586
  // then initializes the V1 and V2 base classes as if by a defaulted default constructor
587
 
588
  struct M { M(); M(int); };
589
  struct N : M { using M::M; };
590
  struct O : M {};
591
  struct P : N, O { using N::N; using O::O; };
592
- P p(0); // OK: use M(0) to initialize N's base class,
593
  // use M() to initialize O's base class
594
  ```
595
 
596
  — *end example*]
597
 
@@ -822,13 +819,15 @@ source and target of the omitted copy/move operation as simply two
822
  different ways of referring to the same object. If the first parameter
823
  of the selected constructor is an rvalue reference to the object’s type,
824
  the destruction of that object occurs when the target would have been
825
  destroyed; otherwise, the destruction occurs at the later of the times
826
  when the two objects would have been destroyed without the
827
- optimization.[^14] This elision of copy/move operations, called *copy
828
- elision*, is permitted in the following circumstances (which may be
829
- combined to eliminate multiple copies):
 
 
830
 
831
  - in a `return` statement in a function with a class return type, when
832
  the *expression* is the name of a non-volatile object with automatic
833
  storage duration (other than a function parameter or a variable
834
  introduced by the *exception-declaration* of a *handler*
@@ -836,14 +835,14 @@ combined to eliminate multiple copies):
836
  the function return type, the copy/move operation can be omitted by
837
  constructing the object directly into the function call’s return
838
  object
839
  - in a *throw-expression* [[expr.throw]], when the operand is the name
840
  of a non-volatile object with automatic storage duration (other than a
841
- function or catch-clause parameter) whose scope does not extend beyond
842
- the end of the innermost enclosing *try-block* (if there is one), the
843
- copy/move operation can be omitted by constructing the object directly
844
- into the exception object
845
  - in a coroutine [[dcl.fct.def.coroutine]], a copy of a coroutine
846
  parameter can be omitted and references to that copy replaced with
847
  references to the corresponding parameter if the meaning of the
848
  program will be unchanged except for the execution of a constructor
849
  and destructor for the parameter copy object
@@ -859,12 +858,12 @@ combined to eliminate multiple copies):
859
 
860
  Copy elision is not permitted where an expression is evaluated in a
861
  context requiring a constant expression [[expr.const]] and in constant
862
  initialization [[basic.start.static]].
863
 
864
- [*Note 2*: Copy elision might be performed if the same expression is
865
- evaluated in another context. — *end note*]
866
 
867
  [*Example 1*:
868
 
869
  ``` cpp
870
  class Thing {
@@ -893,54 +892,25 @@ constexpr A g() {
893
 
894
  constexpr A a; // well-formed, a.p points to a
895
  constexpr A b = g(); // error: b.p would be dangling[expr.const]
896
 
897
  void h() {
898
- A c = g(); // well-formed, c.p may point to c or to an ephemeral temporary
899
  }
900
  ```
901
 
902
  Here the criteria for elision can eliminate the copying of the object
903
  `t` with automatic storage duration into the result object for the
904
- function call `f()`, which is the global object `t2`. Effectively, the
905
- construction of the local object `t` can be viewed as directly
906
- initializing the global object `t2`, and that object’s destruction will
907
- occur at program exit. Adding a move constructor to `Thing` has the same
908
- effect, but it is the move construction from the object with automatic
909
- storage duration to `t2` that is elided.
910
 
911
  — *end example*]
912
 
913
- An *implicitly movable entity* is a variable of automatic storage
914
- duration that is either a non-volatile object or an rvalue reference to
915
- a non-volatile object type. In the following copy-initialization
916
- contexts, a move operation might be used instead of a copy operation:
917
-
918
- - If the *expression* in a `return` [[stmt.return]] or `co_return`
919
- [[stmt.return.coroutine]] statement is a (possibly parenthesized)
920
- *id-expression* that names an implicitly movable entity declared in
921
- the body or *parameter-declaration-clause* of the innermost enclosing
922
- function or *lambda-expression*, or
923
- - if the operand of a *throw-expression* [[expr.throw]] is a (possibly
924
- parenthesized) *id-expression* that names an implicitly movable entity
925
- whose scope does not extend beyond the *compound-statement* of the
926
- innermost *try-block* or *function-try-block* (if any) whose
927
- *compound-statement* or *ctor-initializer* encloses the
928
- *throw-expression*,
929
-
930
- overload resolution to select the constructor for the copy or the
931
- `return_value` overload to call is first performed as if the expression
932
- or operand were an rvalue. If the first overload resolution fails or was
933
- not performed, overload resolution is performed again, considering the
934
- expression or operand as an lvalue.
935
-
936
- [*Note 3*: This two-stage overload resolution must be performed
937
- regardless of whether copy elision will occur. It determines the
938
- constructor or the `return_value` overload to be called if elision is
939
- not performed, and the selected constructor or `return_value` overload
940
- must be accessible even if the call is elided. — *end note*]
941
-
942
  [*Example 2*:
943
 
944
  ``` cpp
945
  class Thing {
946
  public:
@@ -952,24 +922,44 @@ private:
952
  };
953
 
954
  Thing f(bool b) {
955
  Thing t;
956
  if (b)
957
- throw t; // OK: Thing(Thing&&) used (or elided) to throw t
958
- return t; // OK: Thing(Thing&&) used (or elided) to return t
959
  }
960
 
961
- Thing t2 = f(false); // OK: no extra copy/move performed, t2 constructed by call to f
962
 
963
  struct Weird {
964
  Weird();
965
  Weird(Weird&);
966
  };
967
 
968
- Weird g() {
969
- Weird w;
970
- return w; // OK: first overload resolution fails, second overload resolution selects Weird(Weird&)
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
971
  }
972
  ```
973
 
974
  — *end example*]
975
 
 
1
  ## Initialization <a id="class.init">[[class.init]]</a>
2
 
3
+ ### General <a id="class.init.general">[[class.init.general]]</a>
4
+
5
  When no initializer is specified for an object of (possibly
6
  cv-qualified) class type (or array thereof), or the initializer has the
7
  form `()`, the object is initialized as specified in  [[dcl.init]].
8
 
9
  An object of class type (or array thereof) can be explicitly
 
63
  ```
64
 
65
  Here, `complex::complex(double)` is called for the initialization of
66
  `v[0]` and `v[3]`, `complex::complex({}double, double)` is called for
67
  the initialization of `v[1]`, `complex::complex()` is called for the
68
+ initialization of `v[2]`, `v[4]`, and `v[5]`. For another example,
69
 
70
  ``` cpp
71
  struct X {
72
  int i;
73
  float f;
 
120
  mem-initializer-id:
121
  class-or-decltype
122
  identifier
123
  ```
124
 
125
+ Lookup for an unqualified name in a *mem-initializer-id* ignores the
126
+ constructor’s function parameter scope.
 
 
127
 
128
  [*Note 1*: If the constructor’s class contains a member with the same
129
  name as a direct or virtual base class of the class, a
130
  *mem-initializer-id* naming the member or base class and composed of a
131
  single identifier refers to the class member. A *mem-initializer-id* for
132
+ the hidden base class can be specified using a qualified
133
  name. — *end note*]
134
 
135
  Unless the *mem-initializer-id* names the constructor’s class, a
136
  non-static data member of the constructor’s class, or a direct or
137
  virtual base of that class, the *mem-initializer* is ill-formed.
 
150
  ```
151
 
152
  — *end example*]
153
 
154
  If a *mem-initializer-id* is ambiguous because it designates both a
155
+ direct non-virtual base class and an indirect virtual base class, the
156
  *mem-initializer* is ill-formed.
157
 
158
  [*Example 2*:
159
 
160
  ``` cpp
 
238
  };
239
  ```
240
 
241
  — *end example*]
242
 
243
+ In a non-delegating constructor other than an implicitly-defined
244
+ copy/move constructor [[class.copy.ctor]], if a given potentially
245
+ constructed subobject is not designated by a *mem-initializer-id*
246
+ (including the case where there is no *mem-initializer-list* because the
247
+ constructor has no *ctor-initializer*), then
248
 
249
  - if the entity is a non-static data member that has a default member
250
  initializer [[class.mem]] and either
251
  - the constructor’s class is a union [[class.union]], and no other
252
  variant member of that union is designated by a *mem-initializer-id*
 
261
  [[class.union.anon]], no initialization is performed;
262
  - otherwise, the entity is default-initialized [[dcl.init]].
263
 
264
  [*Note 3*: An abstract class [[class.abstract]] is never a most derived
265
  class, thus its constructors never initialize virtual base classes,
266
+ therefore the corresponding *mem-initializer*s can be
267
  omitted. — *end note*]
268
 
269
  An attempt to initialize more than one non-static data member of a union
270
  renders the program ill-formed.
271
 
 
287
  B(int);
288
  };
289
 
290
  struct C {
291
  C() { } // initializes members as follows:
292
+ A a; // OK, calls A::A()
293
  const B b; // error: B has no default constructor
294
+ int i; // OK, i has indeterminate value
295
+ int j = 5; // OK, j has the value 5
296
  };
297
  ```
298
 
299
  — *end example*]
300
 
 
400
  C c(4); // use V()
401
  ```
402
 
403
  — *end example*]
404
 
405
+ [*Note 7*: The *expression-list* or *braced-init-list* of a
406
+ *mem-initializer* is in the function parameter scope of the constructor
407
+ and can use `this` to refer to the object being
408
+ initialized. — *end note*]
409
 
410
  [*Example 10*:
411
 
412
  ``` cpp
413
  class X {
 
426
  the constructor parameter `i`, and initializes `X::j` with the value of
427
  `X::i`; this takes place each time an object of class `X` is created.
428
 
429
  — *end example*]
430
 
 
 
 
 
 
431
  Member functions (including virtual member functions, [[class.virtual]])
432
  can be called for an object under construction. Similarly, an object
433
  under construction can be the operand of the `typeid` operator
434
  [[expr.typeid]] or of a `dynamic_cast` [[expr.dynamic.cast]]. However,
435
  if these operations are performed in a *ctor-initializer* (or in a
 
466
  };
467
  ```
468
 
469
  — *end example*]
470
 
471
+ [*Note 8*: [[class.cdtor]] describes the results of virtual function
472
  calls, `typeid` and `dynamic_cast`s during construction for the
473
  well-defined cases; that is, describes the polymorphic behavior of an
474
  object under construction. — *end note*]
475
 
476
  A *mem-initializer* followed by an ellipsis is a pack expansion
 
520
  int x;
521
  int y = get();
522
  };
523
 
524
  void test() {
525
+ D1 d(2, 3, 4); // OK, B1 is initialized by calling B1(2, 3, 4),
526
  // then d.x is default-initialized (no initialization is performed),
527
  // then d.y is initialized by calling get()
528
+ D1 e; // error: D1 has no default constructor
529
  }
530
 
531
  struct D2 : B2 {
532
  using B2::B2;
533
  B1 b;
534
  };
535
 
536
+ D2 f(1.0); // error: B1 has no default constructor
537
 
538
  struct W { W(int); };
539
  struct X : virtual W { using W::W; X() = delete; };
540
  struct Y : X { using X::X; };
541
  struct Z : Y, virtual W { using Y::Y; };
542
+ Z z(0); // OK, initialization of Y does not invoke default constructor of X
543
 
544
  template<class T> struct Log : T {
545
  using T::T; // inherits all constructors from class T
546
  ~Log() { std::clog << "Destroying wrapper" << std::endl; }
547
  };
 
577
  using V1::V1;
578
  using V2::V2;
579
  };
580
 
581
  D1 d1(0); // error: ambiguous
582
+ D2 d2(0); // OK, initializes virtual B base class, which initializes the A base class
583
  // then initializes the V1 and V2 base classes as if by a defaulted default constructor
584
 
585
  struct M { M(); M(int); };
586
  struct N : M { using M::M; };
587
  struct O : M {};
588
  struct P : N, O { using N::N; using O::O; };
589
+ P p(0); // OK, use M(0) to initialize N's base class,
590
  // use M() to initialize O's base class
591
  ```
592
 
593
  — *end example*]
594
 
 
819
  different ways of referring to the same object. If the first parameter
820
  of the selected constructor is an rvalue reference to the object’s type,
821
  the destruction of that object occurs when the target would have been
822
  destroyed; otherwise, the destruction occurs at the later of the times
823
  when the two objects would have been destroyed without the
824
+ optimization.[^14]
825
+
826
+ This elision of copy/move operations, called *copy elision*, is
827
+ permitted in the following circumstances (which may be combined to
828
+ eliminate multiple copies):
829
 
830
  - in a `return` statement in a function with a class return type, when
831
  the *expression* is the name of a non-volatile object with automatic
832
  storage duration (other than a function parameter or a variable
833
  introduced by the *exception-declaration* of a *handler*
 
835
  the function return type, the copy/move operation can be omitted by
836
  constructing the object directly into the function call’s return
837
  object
838
  - in a *throw-expression* [[expr.throw]], when the operand is the name
839
  of a non-volatile object with automatic storage duration (other than a
840
+ function or catch-clause parameter) that belongs to a scope that does
841
+ not contain the innermost enclosing *compound-statement* associated
842
+ with a *try-block* (if there is one), the copy/move operation can be
843
+ omitted by constructing the object directly into the exception object
844
  - in a coroutine [[dcl.fct.def.coroutine]], a copy of a coroutine
845
  parameter can be omitted and references to that copy replaced with
846
  references to the corresponding parameter if the meaning of the
847
  program will be unchanged except for the execution of a constructor
848
  and destructor for the parameter copy object
 
858
 
859
  Copy elision is not permitted where an expression is evaluated in a
860
  context requiring a constant expression [[expr.const]] and in constant
861
  initialization [[basic.start.static]].
862
 
863
+ [*Note 2*: It is possible that copy elision is performed if the same
864
+ expression is evaluated in another context. — *end note*]
865
 
866
  [*Example 1*:
867
 
868
  ``` cpp
869
  class Thing {
 
892
 
893
  constexpr A a; // well-formed, a.p points to a
894
  constexpr A b = g(); // error: b.p would be dangling[expr.const]
895
 
896
  void h() {
897
+ A c = g(); // well-formed, c.p can point to c or be dangling
898
  }
899
  ```
900
 
901
  Here the criteria for elision can eliminate the copying of the object
902
  `t` with automatic storage duration into the result object for the
903
+ function call `f()`, which is the non-local object `t2`. Effectively,
904
+ the construction of `t` can be viewed as directly initializing `t2`, and
905
+ that object’s destruction will occur at program exit. Adding a move
906
+ constructor to `Thing` has the same effect, but it is the move
907
+ construction from the object with automatic storage duration to `t2`
908
+ that is elided.
909
 
910
  — *end example*]
911
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
912
  [*Example 2*:
913
 
914
  ``` cpp
915
  class Thing {
916
  public:
 
922
  };
923
 
924
  Thing f(bool b) {
925
  Thing t;
926
  if (b)
927
+ throw t; // OK, Thing(Thing&&) used (or elided) to throw t
928
+ return t; // OK, Thing(Thing&&) used (or elided) to return t
929
  }
930
 
931
+ Thing t2 = f(false); // OK, no extra copy/move performed, t2 constructed by call to f
932
 
933
  struct Weird {
934
  Weird();
935
  Weird(Weird&);
936
  };
937
 
938
+ Weird g(bool b) {
939
+ static Weird w1;
940
+ Weird w2;
941
+ if (b)
942
+ return w1; // OK, uses Weird(Weird&)
943
+ else
944
+ return w2; // error: w2 in this context is an xvalue
945
+ }
946
+
947
+ int& h(bool b, int i) {
948
+ static int s;
949
+ if (b)
950
+ return s; // OK
951
+ else
952
+ return i; // error: i is an xvalue
953
+ }
954
+
955
+ decltype(auto) h2(Thing t) {
956
+ return t; // OK, t is an xvalue and h2's return type is Thing
957
+ }
958
+
959
+ decltype(auto) h3(Thing t) {
960
+ return (t); // OK, (t) is an xvalue and h3's return type is Thing&&
961
  }
962
  ```
963
 
964
  — *end example*]
965