From Jason Turner

[class.dtor]

Diff to HTML by rtfpessoa

Files changed (1) hide show
  1. tmp/tmp9mijd2q5/{from.md → to.md} +58 -38
tmp/tmp9mijd2q5/{from.md → to.md} RENAMED
@@ -1,26 +1,43 @@
1
  ## Destructors <a id="class.dtor">[[class.dtor]]</a>
2
 
3
- A special declarator syntax using an optional *function-specifier* (
4
- [[dcl.fct.spec]]) followed by `~` followed by the destructor’s class
5
- name followed by an empty parameter list is used to declare the
6
- destructor in a class definition. In such a declaration, the `~`
7
- followed by the destructor’s class name can be enclosed in optional
8
- parentheses; such parentheses are ignored. A *typedef-name* shall not be
9
- used as the *class-name* following the `~` in the declarator for a
10
- destructor declaration.
11
 
12
- A destructor is used to destroy objects of its class type. A destructor
13
- takes no parameters, and no return type can be specified for it (not
14
- even `void`). The address of a destructor shall not be taken. A
15
- destructor shall not be `static`. A destructor can be invoked for a
16
- `const`, `volatile` or `const` `volatile` object. A destructor shall not
17
- be declared `const`, `volatile` or `const` `volatile` ([[class.this]]).
18
- `const` and `volatile` semantics ([[dcl.type.cv]]) are not applied on
19
- an object under destruction. They stop being in effect when the
20
- destructor for the most derived object ([[intro.object]]) starts. A
21
- destructor shall not be declared with a *ref-qualifier*.
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
22
 
23
  A declaration of a destructor that does not have an
24
  *exception-specification* is implicitly considered to have the same
25
  *exception-specification* as an implicit declaration ([[except.spec]]).
26
 
@@ -30,15 +47,13 @@ destructor is an `inline` `public` member of its class.
30
 
31
  A defaulted destructor for a class `X` is defined as deleted if:
32
 
33
  - `X` is a union-like class that has a variant member with a non-trivial
34
  destructor,
35
- - any of the non-static data members has class type `M` (or array
36
  thereof) and `M` has a deleted destructor or a destructor that is
37
  inaccessible from the defaulted destructor,
38
- - any direct or virtual base class has a deleted destructor or a
39
- destructor that is inaccessible from the defaulted destructor,
40
  - or, for a virtual destructor, lookup of the non-array deallocation
41
  function results in an ambiguity or in a function that is deleted or
42
  inaccessible from the defaulted destructor.
43
 
44
  A destructor is trivial if it is not user-provided and if:
@@ -82,30 +97,33 @@ defined. If a class has a base class with a virtual destructor, its
82
  destructor (whether user- or implicitly-declared) is virtual.
83
 
84
  some language constructs have special semantics when used during
85
  destruction; see  [[class.cdtor]].
86
 
87
- Destructors are invoked implicitly
88
 
89
- - for constructed objects with static storage duration (
90
  [[basic.stc.static]]) at program termination ([[basic.start.term]]),
91
- - for constructed objects with thread storage duration (
92
  [[basic.stc.thread]]) at thread exit,
93
- - for constructed objects with automatic storage duration (
94
  [[basic.stc.auto]]) when the block in which an object is created
95
  exits ([[stmt.dcl]]),
96
- - for constructed temporary objects when the lifetime of a temporary
97
- object ends ([[class.temporary]]),
98
- - for constructed objects allocated by a *new-expression* (
99
- [[expr.new]]), through use of a *delete-expression* (
100
- [[expr.delete]]),
101
- - in several situations due to the handling of exceptions (
102
- [[except.handle]]).
103
 
104
- A program is ill-formed if an object of class type or array thereof is
105
- declared and the destructor for the class is not accessible at the point
106
- of the declaration. Destructors can also be invoked explicitly.
 
 
 
 
 
 
 
 
107
 
108
  At the point of definition of a virtual destructor (including an
109
  implicit definition ([[class.copy]])), the non-array deallocation
110
  function is looked up in the scope of the destructor’s class (
111
  [[class.member.lookup]]), and, if no declaration is found, the function
@@ -117,14 +135,16 @@ deallocation function corresponding to the dynamic type of an object is
117
  available for the *delete-expression* ([[class.free]]).
118
 
119
  In an explicit destructor call, the destructor name appears as a `~`
120
  followed by a *type-name* or *decltype-specifier* that denotes the
121
  destructor’s class type. The invocation of a destructor is subject to
122
- the usual rules for member functions ([[class.mfct]]), that is, if the
123
  object is not of the destructor’s class type and not of a class derived
124
- from the destructor’s class type, the program has undefined behavior
125
- (except that invoking `delete` on a null pointer has no effect).
 
 
126
 
127
  ``` cpp
128
  struct B {
129
  virtual ~B() { }
130
  };
 
1
  ## Destructors <a id="class.dtor">[[class.dtor]]</a>
2
 
3
+ A declaration of a destructor uses a function declarator ([[dcl.fct]])
4
+ of the form
 
 
 
 
 
 
5
 
6
+ ``` bnf
7
+ ptr-declarator '(' parameter-declaration-clause ')' exception-specificationₒₚₜ attribute-specifier-seqₒₚₜ
8
+ ```
9
+
10
+ where the *ptr-declarator* consists solely of an *id-expression*, an
11
+ optional *attribute-specifier-seq*, and optional surrounding
12
+ parentheses, and the *id-expression* has one of the following forms:
13
+
14
+ - in a *member-declaration* that belongs to the *member-specification*
15
+ of a class but is not a friend declaration ([[class.friend]]), the
16
+ *id-expression* is `~`*class-name* and the *class-name* is the
17
+ injected-class-name (Clause  [[class]]) of the immediately-enclosing
18
+ class;
19
+ - in a *member-declaration* that belongs to the *member-specification*
20
+ of a class template but is not a friend declaration, the
21
+ *id-expression* is `~`*class-name* and the *class-name* names the
22
+ current instantiation ([[temp.dep.type]]) of the
23
+ immediately-enclosing class template; or
24
+ - in a declaration at namespace scope or in a friend declaration, the
25
+ *id-expression* is *nested-name-specifier* `~`*class-name* and the
26
+ *class-name* names the same class as the *nested-name-specifier*.
27
+
28
+ The *class-name* shall not be a *typedef-name*. A destructor shall take
29
+ no arguments ([[dcl.fct]]). In a destructor declaration, each
30
+ *decl-specifier* of the optional *decl-specifier-seq* shall be `friend`,
31
+ `inline`, or `virtual`.
32
+
33
+ A destructor is used to destroy objects of its class type. The address
34
+ of a destructor shall not be taken. A destructor can be invoked for a
35
+ `const`, `volatile` or `const` `volatile` object. `const` and `volatile`
36
+ semantics ([[dcl.type.cv]]) are not applied on an object under
37
+ destruction. They stop being in effect when the destructor for the most
38
+ derived object ([[intro.object]]) starts.
39
 
40
  A declaration of a destructor that does not have an
41
  *exception-specification* is implicitly considered to have the same
42
  *exception-specification* as an implicit declaration ([[except.spec]]).
43
 
 
47
 
48
  A defaulted destructor for a class `X` is defined as deleted if:
49
 
50
  - `X` is a union-like class that has a variant member with a non-trivial
51
  destructor,
52
+ - any potentially constructed subobject has class type `M` (or array
53
  thereof) and `M` has a deleted destructor or a destructor that is
54
  inaccessible from the defaulted destructor,
 
 
55
  - or, for a virtual destructor, lookup of the non-array deallocation
56
  function results in an ambiguity or in a function that is deleted or
57
  inaccessible from the defaulted destructor.
58
 
59
  A destructor is trivial if it is not user-provided and if:
 
97
  destructor (whether user- or implicitly-declared) is virtual.
98
 
99
  some language constructs have special semantics when used during
100
  destruction; see  [[class.cdtor]].
101
 
102
+ A destructor is invoked implicitly
103
 
104
+ - for a constructed object with static storage duration (
105
  [[basic.stc.static]]) at program termination ([[basic.start.term]]),
106
+ - for a constructed object with thread storage duration (
107
  [[basic.stc.thread]]) at thread exit,
108
+ - for a constructed object with automatic storage duration (
109
  [[basic.stc.auto]]) when the block in which an object is created
110
  exits ([[stmt.dcl]]),
111
+ - for a constructed temporary object when its lifetime ends (
112
+ [[class.temporary]]).
 
 
 
 
 
113
 
114
+ In each case, the context of the invocation is the context of the
115
+ construction of the object. A destructor is also invoked implicitly
116
+ through use of a *delete-expression* ([[expr.delete]]) for a
117
+ constructed object allocated by a *new-expression* ([[expr.new]]); the
118
+ context of the invocation is the *delete-expression*. An array of class
119
+ type contains several subobjects for each of which the destructor is
120
+ invoked. A destructor can also be invoked explicitly. A destructor is
121
+ *potentially invoked* if it is invoked or as specified in  [[expr.new]]
122
+ and  [[class.base.init]]. A program is ill-formed if a destructor that
123
+ is potentially invoked is deleted or not accessible from the context of
124
+ the invocation.
125
 
126
  At the point of definition of a virtual destructor (including an
127
  implicit definition ([[class.copy]])), the non-array deallocation
128
  function is looked up in the scope of the destructor’s class (
129
  [[class.member.lookup]]), and, if no declaration is found, the function
 
135
  available for the *delete-expression* ([[class.free]]).
136
 
137
  In an explicit destructor call, the destructor name appears as a `~`
138
  followed by a *type-name* or *decltype-specifier* that denotes the
139
  destructor’s class type. The invocation of a destructor is subject to
140
+ the usual rules for member functions ([[class.mfct]]); that is, if the
141
  object is not of the destructor’s class type and not of a class derived
142
+ from the destructor’s class type (including when the destructor is
143
+ invoked via a null pointer value), the program has undefined behavior.
144
+ invoking `delete` on a null pointer does not call the destructor; see
145
+ [[expr.delete]].
146
 
147
  ``` cpp
148
  struct B {
149
  virtual ~B() { }
150
  };