tmp/tmpjqjnuubx/{from.md → to.md}
RENAMED
|
@@ -7,15 +7,15 @@ 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
|
| 13 |
-
template *template-parameter* is
|
| 14 |
-
not visible at the point of
|
| 15 |
-
selected had it been visible, the
|
| 16 |
-
is required.
|
| 17 |
|
| 18 |
``` cpp
|
| 19 |
template<class T> class A { // primary template
|
| 20 |
int x;
|
| 21 |
};
|
|
@@ -30,10 +30,26 @@ C<A> c; // V<int> within C<A> uses the primary template,
|
|
| 30 |
// so c.y.x has type int
|
| 31 |
// V<int*> within C<A> uses the partial specialization,
|
| 32 |
// so c.z.x has type long
|
| 33 |
```
|
| 34 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 35 |
``` cpp
|
| 36 |
template<class T> class A { /* ... */ };
|
| 37 |
template<class T, class U = T> class B { /* ... */ };
|
| 38 |
template <class ... Types> class C { /* ... */ };
|
| 39 |
|
|
@@ -47,22 +63,10 @@ X<C> xc; // ill-formed: a template parameter pack does not match a te
|
|
| 47 |
Y<A> ya; // OK
|
| 48 |
Y<B> yb; // OK
|
| 49 |
Y<C> yc; // OK
|
| 50 |
```
|
| 51 |
|
| 52 |
-
A *template-argument* matches a template *template-parameter* (call it
|
| 53 |
-
`P`) when each of the template parameters in the
|
| 54 |
-
*template-parameter-list* of the *template-argument*’s corresponding
|
| 55 |
-
class template or alias template (call it `A`) matches the corresponding
|
| 56 |
-
template parameter in the *template-parameter-list* of `P`. When `P`’s
|
| 57 |
-
*template-parameter-list* contains a template parameter pack (
|
| 58 |
-
[[temp.variadic]]), the template parameter pack will match zero or more
|
| 59 |
-
template parameters or template parameter packs in the
|
| 60 |
-
*template-parameter-list* of `A` with the same type and form as the
|
| 61 |
-
template parameter pack in `P` (ignoring whether those template
|
| 62 |
-
parameters are template parameter packs)
|
| 63 |
-
|
| 64 |
``` cpp
|
| 65 |
template <class T> struct eval;
|
| 66 |
|
| 67 |
template <template <class, class...> class TT, class T1, class... Rest>
|
| 68 |
struct eval<TT<T1, Rest...>> { };
|
|
|
|
| 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 is required.
|
| 17 |
|
| 18 |
``` cpp
|
| 19 |
template<class T> class A { // primary template
|
| 20 |
int x;
|
| 21 |
};
|
|
|
|
| 30 |
// so c.y.x has type int
|
| 31 |
// V<int*> within C<A> uses the partial specialization,
|
| 32 |
// so c.z.x has type long
|
| 33 |
```
|
| 34 |
|
| 35 |
+
A *template-argument* matches a template *template-parameter* (call it
|
| 36 |
+
`P`) when each of the template parameters in the
|
| 37 |
+
*template-parameter-list* of the *template-argument*’s corresponding
|
| 38 |
+
class template or alias template (call it `A`) matches the corresponding
|
| 39 |
+
template parameter in the *template-parameter-list* of `P`. Two template
|
| 40 |
+
parameters match if they are of the same kind (type, non-type,
|
| 41 |
+
template), for non-type *template-parameter*s, their types are
|
| 42 |
+
equivalent ([[temp.over.link]]), and for template
|
| 43 |
+
*template-parameter*s, each of their corresponding *template-parameter*s
|
| 44 |
+
matches, recursively. When `P`’s *template-parameter-list* contains a
|
| 45 |
+
template parameter pack ([[temp.variadic]]), the template parameter
|
| 46 |
+
pack will match zero or more template parameters or template parameter
|
| 47 |
+
packs in the *template-parameter-list* of `A` with the same type and
|
| 48 |
+
form as the template parameter pack in `P` (ignoring whether those
|
| 49 |
+
template parameters are template parameter packs).
|
| 50 |
+
|
| 51 |
``` cpp
|
| 52 |
template<class T> class A { /* ... */ };
|
| 53 |
template<class T, class U = T> class B { /* ... */ };
|
| 54 |
template <class ... Types> class C { /* ... */ };
|
| 55 |
|
|
|
|
| 63 |
Y<A> ya; // OK
|
| 64 |
Y<B> yb; // OK
|
| 65 |
Y<C> yc; // OK
|
| 66 |
```
|
| 67 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 68 |
``` cpp
|
| 69 |
template <class T> struct eval;
|
| 70 |
|
| 71 |
template <template <class, class...> class TT, class T1, class... Rest>
|
| 72 |
struct eval<TT<T1, Rest...>> { };
|