Reputation: 149
What I understood from the standard (I refer to the text from n4849 draft)
(§13.9.1-2) [temp.inst] The implicit instantiation of a class template specialization causes (2.1) — the implicit instantiation of the declarations, but not of the definitions, of the non-deleted class member functions, member classes, scoped member enumerations, static data members, member templates, and friends; and (2.2) — the implicit instantiation of the definitions of deleted member functions, unscoped member enumerations, and member anonymous unions.
(§13.9.2-11) [temp.explicit] An explicit instantiation that names a class template specialization is also an explicit instantiation of the same kind (declaration or definition) of each of its members (not including members inherited from base classes and members that are templates) that has not been previously explicitly specialized in the translation unit containing the explicit instantiation, ....
is that an implicit instantiation leads to use the declarations of the members of class template as from the primary template (or a better matching partial specialization), whereas an explicit instantiation leads to use both declaration and definition (or a better matching partial specialization or an explicit specialization) but only the declaration in case of members template.
Now, everything seems clear in the following example 1:
template<class T1> class A1 {
template<class T2> class B{
void func();
};
};
/*
// this would solve, providing a specialization of B for A1<char>,
//with or without keeping the next explicit instantiation
template<> class A1<char>{
template<class T2> class B{
void func(); // of course, func2 (different) name may be used,
// to be replicated in last line of code of this example
};
}
*/
// explicit instantiation not producing any definition for B from the primary template
template class A1<char>;
template<> template<class T2> void A1<char>::B<T2>::func(){};
// error because the template B is not yet defined for the specialization A1<char>,
// and the same would happen also after removing the explicit instantiation,
// as also the consequent implicit instantiation provided by "A1<char>" in
// this line of code does not push to generate the definition of
// the template class B inside A1 for the specialization A1<char>.
But I have doubts in the following example 2:
template<class T1> class A2 {
class B{
void func();
};
};
//template class A2<char>;
template<> void A2<char>::B::func(){};
this example compiles even without the explicit instantiation.
How this may happen ? That is, what causes the definition of the class B
for the specialization A2<char>
? Mainly, where in the standard is there a rule to clarify it ?
Upvotes: 2
Views: 89