From Jason Turner

[temp.class.spec]

Diff to HTML by rtfpessoa

Files changed (1) hide show
  1. tmp/tmp8iji88lr/{from.md → to.md} +94 -26
tmp/tmp8iji88lr/{from.md → to.md} RENAMED
@@ -5,21 +5,21 @@ template name is an identifier. A template declaration in which the
5
  class template name is a *simple-template-id* is a *partial
6
  specialization* of the class template named in the *simple-template-id*.
7
  A partial specialization of a class template provides an alternative
8
  definition of the template that is used instead of the primary
9
  definition when the arguments in a specialization match those given in
10
- the partial specialization ([[temp.class.spec.match]]). The primary
11
  template shall be declared before any specializations of that template.
12
  A partial specialization shall be declared before the first use of a
13
  class template specialization that would make use of the partial
14
  specialization as the result of an implicit or explicit instantiation in
15
  every translation unit in which such a use occurs; no diagnostic is
16
  required.
17
 
18
  Each class template partial specialization is a distinct template and
19
  definitions shall be provided for the members of a template partial
20
- specialization ([[temp.class.spec.mfunc]]).
21
 
22
  [*Example 1*:
23
 
24
  ``` cpp
25
  template<class T1, class T2, int I> class A { };
@@ -33,25 +33,46 @@ The first declaration declares the primary (unspecialized) class
33
  template. The second and subsequent declarations declare partial
34
  specializations of the primary template.
35
 
36
  — *end example*]
37
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
38
  The template parameters are specified in the angle bracket enclosed list
39
  that immediately follows the keyword `template`. For partial
40
  specializations, the template argument list is explicitly written
41
  immediately following the class template name. For primary templates,
42
  this list is implicitly described by the template parameter list.
43
  Specifically, the order of the template arguments is the sequence in
44
  which they appear in the template parameter list.
45
 
46
- [*Example 2*: The template argument list for the primary template in
47
  the example above is `<T1,` `T2,` `I>`. — *end example*]
48
 
49
  [*Note 1*:
50
 
51
- The template argument list shall not be specified in the primary
52
- template declaration. For example,
53
 
54
  ``` cpp
55
  template<class T1, class T2, int I>
56
  class A<T1, T2, I> { }; // error
57
  ```
@@ -60,11 +81,11 @@ class A<T1, T2, I> { }; // error
60
 
61
  A class template partial specialization may be declared in any scope in
62
  which the corresponding primary template may be defined (
63
  [[namespace.memdef]], [[class.mem]], [[temp.mem]]).
64
 
65
- [*Example 3*:
66
 
67
  ``` cpp
68
  template<class T> struct A {
69
  struct C {
70
  template<class T2> struct B { };
@@ -86,11 +107,11 @@ lookup. Rather, when the primary template name is used, any
86
  previously-declared partial specializations of the primary template are
87
  also considered. One consequence is that a *using-declaration* which
88
  refers to a class template does not restrict the set of partial
89
  specializations which may be found through the *using-declaration*.
90
 
91
- [*Example 4*:
92
 
93
  ``` cpp
94
  namespace N {
95
  template<class T1, class T2> class A { }; // primary template
96
  }
@@ -114,28 +135,37 @@ Within the argument list of a class template partial specialization, the
114
  following restrictions apply:
115
 
116
  - The type of a template parameter corresponding to a specialized
117
  non-type argument shall not be dependent on a parameter of the
118
  specialization.
119
- \[*Example 5*:
120
  ``` cpp
121
  template <class T, T t> struct C {};
122
  template <class T> struct C<T, 1>; // error
123
 
124
  template< int X, int (*array_ptr)[X] > class A {};
125
  int array[5];
126
  template< int X > class A<X,&array> { }; // error
127
  ```
128
 
129
  — *end example*]
130
- - The specialization shall be more specialized than the primary
131
- template ([[temp.class.order]]).
132
  - The template parameter list of a specialization shall not contain
133
- default template argument values.[^4]
134
- - An argument shall not contain an unexpanded parameter pack. If an
135
- argument is a pack expansion ([[temp.variadic]]), it shall be the
136
- last argument in the template argument list.
 
 
 
 
 
 
 
 
 
137
 
138
  #### Matching of class template partial specializations <a id="temp.class.spec.match">[[temp.class.spec.match]]</a>
139
 
140
  When a class template is used in a context that requires an
141
  instantiation of the class, it is necessary to determine whether the
@@ -145,21 +175,23 @@ arguments of the class template specialization with the template
145
  argument lists of the partial specializations.
146
 
147
  - If exactly one matching specialization is found, the instantiation is
148
  generated from that specialization.
149
  - If more than one matching specialization is found, the partial order
150
- rules ([[temp.class.order]]) are used to determine whether one of the
151
  specializations is more specialized than the others. If none of the
152
  specializations is more specialized than all of the other matching
153
  specializations, then the use of the class template is ambiguous and
154
  the program is ill-formed.
155
  - If no matches are found, the instantiation is generated from the
156
  primary template.
157
 
158
  A partial specialization matches a given actual template argument list
159
  if the template arguments of the partial specialization can be deduced
160
- from the actual template argument list ([[temp.deduct]]).
 
 
161
 
162
  [*Example 1*:
163
 
164
  ``` cpp
165
  template<class T1, class T2, int I> class A { }; // #1
@@ -175,15 +207,31 @@ A<int, char*, 1> a4; // uses #5, T1 is int, T2 is char, I is 1
175
  A<int*, int*, 2> a5; // ambiguous: matches #3 and #5
176
  ```
177
 
178
  — *end example*]
179
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
180
  If the template arguments of a partial specialization cannot be deduced
181
  because of the structure of its *template-parameter-list* and the
182
  *template-id*, the program is ill-formed.
183
 
184
- [*Example 2*:
185
 
186
  ``` cpp
187
  template <int I, int J> struct A {};
188
  template <int I> struct A<I+5, I*2> {}; // error
189
 
@@ -203,15 +251,16 @@ are deduced from the arguments of the primary template.
203
  #### Partial ordering of class template specializations <a id="temp.class.order">[[temp.class.order]]</a>
204
 
205
  For two class template partial specializations, the first is *more
206
  specialized* than the second if, given the following rewrite to two
207
  function templates, the first function template is more specialized than
208
- the second according to the ordering rules for function templates (
209
- [[temp.func.order]]):
210
 
211
- - Each of the two function templates has the same template parameters as
212
- the corresponding partial specialization.
 
213
  - Each function template has a single function parameter whose type is a
214
  class template specialization where the template arguments are the
215
  corresponding template parameters from the function template for each
216
  template argument in the *template-argument-list* of the
217
  *simple-template-id* of the partial specialization.
@@ -241,21 +290,40 @@ function template *D* is more specialized than the function template
241
  the partial specialization \#1 and the partial specialization \#4 is
242
  more specialized than the partial specialization \#3.
243
 
244
  — *end example*]
245
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
246
  #### Members of class template specializations <a id="temp.class.spec.mfunc">[[temp.class.spec.mfunc]]</a>
247
 
248
  The template parameter list of a member of a class template partial
249
  specialization shall match the template parameter list of the class
250
  template partial specialization. The template argument list of a member
251
  of a class template partial specialization shall match the template
252
  argument list of the class template partial specialization. A class
253
- template specialization is a distinct template. The members of the class
254
- template partial specialization are unrelated to the members of the
255
- primary template. Class template partial specialization members that are
256
- used in a way that requires a definition shall be defined; the
257
  definitions of members of the primary template are never used as
258
  definitions for members of a class template partial specialization. An
259
  explicit specialization of a member of a class template partial
260
  specialization is declared in the same way as an explicit specialization
261
  of the primary template.
@@ -288,11 +356,11 @@ int main() {
288
  A<char,0> a0;
289
  A<char,2> a2;
290
  a0.f(); // OK, uses definition of primary template's member
291
  a2.g(); // OK, uses definition of partial specialization's member
292
  a2.h(); // OK, uses definition of explicit specialization's member
293
- a2.f(); // ill-formed, no definition of f for A<T,2>; the primary template is not used here
294
  }
295
  ```
296
 
297
  — *end example*]
298
 
 
5
  class template name is a *simple-template-id* is a *partial
6
  specialization* of the class template named in the *simple-template-id*.
7
  A partial specialization of a class template provides an alternative
8
  definition of the template that is used instead of the primary
9
  definition when the arguments in a specialization match those given in
10
+ the partial specialization [[temp.class.spec.match]]. The primary
11
  template shall be declared before any specializations of that template.
12
  A partial specialization shall be declared before the first use of a
13
  class template specialization that would make use of the partial
14
  specialization as the result of an implicit or explicit instantiation in
15
  every translation unit in which such a use occurs; no diagnostic is
16
  required.
17
 
18
  Each class template partial specialization is a distinct template and
19
  definitions shall be provided for the members of a template partial
20
+ specialization [[temp.class.spec.mfunc]].
21
 
22
  [*Example 1*:
23
 
24
  ``` cpp
25
  template<class T1, class T2, int I> class A { };
 
33
  template. The second and subsequent declarations declare partial
34
  specializations of the primary template.
35
 
36
  — *end example*]
37
 
38
+ A class template partial specialization may be constrained [[temp.pre]].
39
+
40
+ [*Example 2*:
41
+
42
+ ``` cpp
43
+ template<typename T> concept C = true;
44
+
45
+ template<typename T> struct X { };
46
+ template<typename T> struct X<T*> { }; // #1
47
+ template<C T> struct X<T> { }; // #2
48
+ ```
49
+
50
+ Both partial specializations are more specialized than the primary
51
+ template. \#1 is more specialized because the deduction of its template
52
+ arguments from the template argument list of the class template
53
+ specialization succeeds, while the reverse does not. \#2 is more
54
+ specialized because the template arguments are equivalent, but the
55
+ partial specialization is more constrained [[temp.constr.order]].
56
+
57
+ — *end example*]
58
+
59
  The template parameters are specified in the angle bracket enclosed list
60
  that immediately follows the keyword `template`. For partial
61
  specializations, the template argument list is explicitly written
62
  immediately following the class template name. For primary templates,
63
  this list is implicitly described by the template parameter list.
64
  Specifically, the order of the template arguments is the sequence in
65
  which they appear in the template parameter list.
66
 
67
+ [*Example 3*: The template argument list for the primary template in
68
  the example above is `<T1,` `T2,` `I>`. — *end example*]
69
 
70
  [*Note 1*:
71
 
72
+ The template argument list cannot be specified in the primary template
73
+ declaration. For example,
74
 
75
  ``` cpp
76
  template<class T1, class T2, int I>
77
  class A<T1, T2, I> { }; // error
78
  ```
 
81
 
82
  A class template partial specialization may be declared in any scope in
83
  which the corresponding primary template may be defined (
84
  [[namespace.memdef]], [[class.mem]], [[temp.mem]]).
85
 
86
+ [*Example 4*:
87
 
88
  ``` cpp
89
  template<class T> struct A {
90
  struct C {
91
  template<class T2> struct B { };
 
107
  previously-declared partial specializations of the primary template are
108
  also considered. One consequence is that a *using-declaration* which
109
  refers to a class template does not restrict the set of partial
110
  specializations which may be found through the *using-declaration*.
111
 
112
+ [*Example 5*:
113
 
114
  ``` cpp
115
  namespace N {
116
  template<class T1, class T2> class A { }; // primary template
117
  }
 
135
  following restrictions apply:
136
 
137
  - The type of a template parameter corresponding to a specialized
138
  non-type argument shall not be dependent on a parameter of the
139
  specialization.
140
+ \[*Example 6*:
141
  ``` cpp
142
  template <class T, T t> struct C {};
143
  template <class T> struct C<T, 1>; // error
144
 
145
  template< int X, int (*array_ptr)[X] > class A {};
146
  int array[5];
147
  template< int X > class A<X,&array> { }; // error
148
  ```
149
 
150
  — *end example*]
151
+ - The specialization shall be more specialized than the primary template
152
+ [[temp.class.order]].
153
  - The template parameter list of a specialization shall not contain
154
+ default template argument values.[^8]
155
+ - An argument shall not contain an unexpanded pack. If an argument is a
156
+ pack expansion [[temp.variadic]], it shall be the last argument in the
157
+ template argument list.
158
+
159
+ The usual access checking rules do not apply to non-dependent names used
160
+ to specify template arguments of the *simple-template-id* of the partial
161
+ specialization.
162
+
163
+ [*Note 2*: The template arguments may be private types or objects that
164
+ would normally not be accessible. Dependent names cannot be checked when
165
+ declaring the partial specialization, but will be checked when
166
+ substituting into the partial specialization. — *end note*]
167
 
168
  #### Matching of class template partial specializations <a id="temp.class.spec.match">[[temp.class.spec.match]]</a>
169
 
170
  When a class template is used in a context that requires an
171
  instantiation of the class, it is necessary to determine whether the
 
175
  argument lists of the partial specializations.
176
 
177
  - If exactly one matching specialization is found, the instantiation is
178
  generated from that specialization.
179
  - If more than one matching specialization is found, the partial order
180
+ rules [[temp.class.order]] are used to determine whether one of the
181
  specializations is more specialized than the others. If none of the
182
  specializations is more specialized than all of the other matching
183
  specializations, then the use of the class template is ambiguous and
184
  the program is ill-formed.
185
  - If no matches are found, the instantiation is generated from the
186
  primary template.
187
 
188
  A partial specialization matches a given actual template argument list
189
  if the template arguments of the partial specialization can be deduced
190
+ from the actual template argument list [[temp.deduct]], and the deduced
191
+ template arguments satisfy the associated constraints of the partial
192
+ specialization, if any [[temp.constr.decl]].
193
 
194
  [*Example 1*:
195
 
196
  ``` cpp
197
  template<class T1, class T2, int I> class A { }; // #1
 
207
  A<int*, int*, 2> a5; // ambiguous: matches #3 and #5
208
  ```
209
 
210
  — *end example*]
211
 
212
+ [*Example 2*:
213
+
214
+ ``` cpp
215
+ template<typename T> concept C = requires (T t) { t.f(); };
216
+
217
+ template<typename T> struct S { }; // #1
218
+ template<C T> struct S<T> { }; // #2
219
+
220
+ struct Arg { void f(); };
221
+
222
+ S<int> s1; // uses #1; the constraints of #2 are not satisfied
223
+ S<Arg> s2; // uses #2; both constraints are satisfied but #2 is more specialized
224
+ ```
225
+
226
+ — *end example*]
227
+
228
  If the template arguments of a partial specialization cannot be deduced
229
  because of the structure of its *template-parameter-list* and the
230
  *template-id*, the program is ill-formed.
231
 
232
+ [*Example 3*:
233
 
234
  ``` cpp
235
  template <int I, int J> struct A {};
236
  template <int I> struct A<I+5, I*2> {}; // error
237
 
 
251
  #### Partial ordering of class template specializations <a id="temp.class.order">[[temp.class.order]]</a>
252
 
253
  For two class template partial specializations, the first is *more
254
  specialized* than the second if, given the following rewrite to two
255
  function templates, the first function template is more specialized than
256
+ the second according to the ordering rules for function templates
257
+ [[temp.func.order]]:
258
 
259
+ - Each of the two function templates has the same template parameters
260
+ and associated constraints [[temp.constr.decl]] as the corresponding
261
+ partial specialization.
262
  - Each function template has a single function parameter whose type is a
263
  class template specialization where the template arguments are the
264
  corresponding template parameters from the function template for each
265
  template argument in the *template-argument-list* of the
266
  *simple-template-id* of the partial specialization.
 
290
  the partial specialization \#1 and the partial specialization \#4 is
291
  more specialized than the partial specialization \#3.
292
 
293
  — *end example*]
294
 
295
+ [*Example 2*:
296
+
297
+ ``` cpp
298
+ template<typename T> concept C = requires (T t) { t.f(); };
299
+ template<typename T> concept D = C<T> && requires (T t) { t.f(); };
300
+
301
+ template<typename T> class S { };
302
+ template<C T> class S<T> { }; // #1
303
+ template<D T> class S<T> { }; // #2
304
+
305
+ template<C T> void f(S<T>); // A
306
+ template<D T> void f(S<T>); // B
307
+ ```
308
+
309
+ The partial specialization \#2 is more specialized than \#1 because `B`
310
+ is more specialized than `A`.
311
+
312
+ — *end example*]
313
+
314
  #### Members of class template specializations <a id="temp.class.spec.mfunc">[[temp.class.spec.mfunc]]</a>
315
 
316
  The template parameter list of a member of a class template partial
317
  specialization shall match the template parameter list of the class
318
  template partial specialization. The template argument list of a member
319
  of a class template partial specialization shall match the template
320
  argument list of the class template partial specialization. A class
321
+ template partial specialization is a distinct template. The members of
322
+ the class template partial specialization are unrelated to the members
323
+ of the primary template. Class template partial specialization members
324
+ that are used in a way that requires a definition shall be defined; the
325
  definitions of members of the primary template are never used as
326
  definitions for members of a class template partial specialization. An
327
  explicit specialization of a member of a class template partial
328
  specialization is declared in the same way as an explicit specialization
329
  of the primary template.
 
356
  A<char,0> a0;
357
  A<char,2> a2;
358
  a0.f(); // OK, uses definition of primary template's member
359
  a2.g(); // OK, uses definition of partial specialization's member
360
  a2.h(); // OK, uses definition of explicit specialization's member
361
+ a2.f(); // error: no definition of f for A<T,2>; the primary template is not used here
362
  }
363
  ```
364
 
365
  — *end example*]
366