From Jason Turner

[temp.arg.template]

Diff to HTML by rtfpessoa

Files changed (1) hide show
  1. tmp/tmp8cr2ecn6/{from.md → to.md} +45 -24
tmp/tmp8cr2ecn6/{from.md → to.md} RENAMED
@@ -6,11 +6,11 @@ name of a class template or an alias template, expressed as
6
  only primary class templates are considered when matching the template
7
  template argument with the corresponding parameter; partial
8
  specializations are not considered even if their parameter lists match
9
  that of the template template parameter.
10
 
11
- Any partial specializations ([[temp.class.spec]]) associated with the
12
  primary class template or primary variable template are considered when
13
  a specialization based on the template *template-parameter* is
14
  instantiated. If a specialization is not visible at the point of
15
  instantiation, and it would have been selected had it been visible, the
16
  program is ill-formed, no diagnostic required.
@@ -33,24 +33,25 @@ C<A> c; // V<int> within C<A> uses the primary template, so c.y.x ha
33
  ```
34
 
35
  — *end example*]
36
 
37
  A *template-argument* matches a template *template-parameter* `P` when
38
- `P` is at least as specialized as the *template-argument* `A`. If `P`
39
- contains a parameter pack, then `A` also matches `P` if each of `A`’s
40
- template parameters matches the corresponding template parameter in the
41
- *template-parameter-list* of `P`. Two template parameters match if they
42
- are of the same kind (type, non-type, template), for non-type
43
- *template-parameter*s, their types are equivalent ([[temp.over.link]]),
44
- and for template *template-parameter*s, each of their corresponding
45
- *template-parameter*s matches, recursively. When `P`’s
46
- *template-parameter-list* contains a template parameter pack (
47
- [[temp.variadic]]), the template parameter pack will match zero or more
48
- template parameters or template parameter packs in the
49
- *template-parameter-list* of `A` with the same type and form as the
50
- template parameter pack in `P` (ignoring whether those template
51
- parameters are template parameter packs).
 
52
 
53
  [*Example 2*:
54
 
55
  ``` cpp
56
  template<class T> class A { ... };
@@ -93,27 +94,47 @@ eval<D<int, 17>> eD; // error: D does not match TT in partial special
93
  eval<E<int, float>> eE; // error: E does not match TT in partial specialization
94
  ```
95
 
96
  — *end example*]
97
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
98
  A template *template-parameter* `P` is at least as specialized as a
99
  template *template-argument* `A` if, given the following rewrite to two
100
  function templates, the function template corresponding to `P` is at
101
  least as specialized as the function template corresponding to `A`
102
- according to the partial ordering rules for function templates (
103
- [[temp.func.order]]). Given an invented class template `X` with the
104
- template parameter list of `A` (including default arguments):
 
105
 
106
- - Each of the two function templates has the same template parameters,
107
- respectively, as `P` or `A`.
108
  - Each function template has a single function parameter whose type is a
109
  specialization of `X` with template arguments corresponding to the
110
  template parameters from the respective function template where, for
111
- each template parameter `PP` in the template parameter list of the
112
- function template, a corresponding template argument `AA` is formed.
113
- If `PP` declares a parameter pack, then `AA` is the pack expansion
114
- `PP...` ([[temp.variadic]]); otherwise, `AA` is the *id-expression*
115
  `PP`.
116
 
117
  If the rewrite produces an invalid type, then `P` is not at least as
118
  specialized as `A`.
119
 
 
6
  only primary class templates are considered when matching the template
7
  template argument with the corresponding parameter; partial
8
  specializations are not considered even if their parameter lists match
9
  that of the template template parameter.
10
 
11
+ Any partial specializations [[temp.class.spec]] associated with the
12
  primary class template or primary variable template are considered when
13
  a specialization based on the template *template-parameter* is
14
  instantiated. If a specialization is not visible at the point of
15
  instantiation, and it would have been selected had it been visible, the
16
  program is ill-formed, no diagnostic required.
 
33
  ```
34
 
35
  — *end example*]
36
 
37
  A *template-argument* matches a template *template-parameter* `P` when
38
+ `P` is at least as specialized as the *template-argument* `A`. In this
39
+ comparison, if `P` is unconstrained, the constraints on `A` are not
40
+ considered. If `P` contains a template parameter pack, then `A` also
41
+ matches `P` if each of `A`’s template parameters matches the
42
+ corresponding template parameter in the *template-head* of `P`. Two
43
+ template parameters match if they are of the same kind (type, non-type,
44
+ template), for non-type *template-parameter*s, their types are
45
+ equivalent [[temp.over.link]], and for template *template-parameter*s,
46
+ each of their corresponding *template-parameter*s matches, recursively.
47
+ When `P`’s *template-head* contains a template parameter pack
48
+ [[temp.variadic]], the template parameter pack will match zero or more
49
+ template parameters or template parameter packs in the *template-head*
50
+ of `A` with the same type and form as the template parameter pack in `P`
51
+ (ignoring whether those template parameters are template parameter
52
+ packs).
53
 
54
  [*Example 2*:
55
 
56
  ``` cpp
57
  template<class T> class A { ... };
 
94
  eval<E<int, float>> eE; // error: E does not match TT in partial specialization
95
  ```
96
 
97
  — *end example*]
98
 
99
+ [*Example 4*:
100
+
101
+ ``` cpp
102
+ template<typename T> concept C = requires (T t) { t.f(); };
103
+ template<typename T> concept D = C<T> && requires (T t) { t.g(); };
104
+
105
+ template<template<C> class P> struct S { };
106
+
107
+ template<C> struct X { };
108
+ template<D> struct Y { };
109
+ template<typename T> struct Z { };
110
+
111
+ S<X> s1; // OK, X and P have equivalent constraints
112
+ S<Y> s2; // error: P is not at least as specialized as Y
113
+ S<Z> s3; // OK, P is at least as specialized as Z
114
+ ```
115
+
116
+ — *end example*]
117
+
118
  A template *template-parameter* `P` is at least as specialized as a
119
  template *template-argument* `A` if, given the following rewrite to two
120
  function templates, the function template corresponding to `P` is at
121
  least as specialized as the function template corresponding to `A`
122
+ according to the partial ordering rules for function templates
123
+ [[temp.func.order]]. Given an invented class template `X` with the
124
+ *template-head* of `A` (including default arguments and
125
+ *requires-clause*, if any):
126
 
127
+ - Each of the two function templates has the same template parameters
128
+ and *requires-clause* (if any), respectively, as `P` or `A`.
129
  - Each function template has a single function parameter whose type is a
130
  specialization of `X` with template arguments corresponding to the
131
  template parameters from the respective function template where, for
132
+ each template parameter `PP` in the *template-head* of the function
133
+ template, a corresponding template argument `AA` is formed. If `PP`
134
+ declares a template parameter pack, then `AA` is the pack expansion
135
+ `PP...` [[temp.variadic]]; otherwise, `AA` is the *id-expression*
136
  `PP`.
137
 
138
  If the rewrite produces an invalid type, then `P` is not at least as
139
  specialized as `A`.
140