Suppose the following declaration:
template <typename T> struct MyTemplate;
The following definition of the partial specialization seems to use the same letter T
to refer to different types.
template <typename T> struct MyTemplate<T*> {};
For example, let's take a concrete instantiation:
MyTemplate<int *> c;
Now, consider again the above definition of the partial specialization:
template <typename T> struct MyTemplate<T*> {};
In the first part of this line (i.e. template <typename T>
), T
is int *
. In the second part of the line (i.e. MyTemplate<T*>
), T
is int
!
So, how is the definition of the partial specialization read?
Read it like this:
The primary template says "MyTemplate
is a class template with one type parameter":
template <typename> struct MyTemplate;
The partial specialization says, "whenever there exists a type T
"...
template <typename T>
... such that a specialization of MyTemplate
is requested for the type T *
"...
struct MyTemplate<T *>
... then use this alternative definition of the template.
You could also define explicit specializations. For example, could say "whenever the specialization is requested for type X
, use this alternative definition:
template <> struct MyTemplate<X> { /* ... */ };
Note that explicit specializations of class templates define types, wheras partial specializations define templates.
To see it another way: A partial class template specialization deduces, or pattern-matches, the structure of the class template arguments:
template <typename T> struct MyTemplate<T *>
// ^^^^^^^^^^^^ ^^^^^
// This is a new template Argument passed to the original class
// template parameter
The parameter names of this new template are matched structurally against the argument of the original class template's parameters.
Examples:
MyTemplate<void>
: The type parameter of the class template is void
, and the primary template is used for this specialization.
MyTemplate<int *>
: The type parameter is int *
. There exists a type T
, namely T = int
, such that the requested type parameter is T *
, and so the definition of the partial specialization of the template is used for this specialization.
MyTemplate<X>
: The parameter type is X
, and an explicit specialization has been defined for that parameter type, which is therefore used.