13 Templates [temp]

13.9 Template instantiation and specialization [temp.spec]

13.9.3 Explicit instantiation [temp.explicit]

A class, function, variable, or member template specialization can be explicitly instantiated from its template.
A member function, member class or static data member of a class template can be explicitly instantiated from the member definition associated with its class template.
The syntax for explicit instantiation is:
There are two forms of explicit instantiation: an explicit instantiation definition and an explicit instantiation declaration.
An explicit instantiation declaration begins with the extern keyword.
An explicit instantiation shall not use a storage-class-specifier ([dcl.stc]) other than thread_­local.
An explicit instantiation of a function template, member function of a class template, or variable template shall not use the inline, constexpr, or consteval specifiers.
No attribute-specifier-seq ([dcl.attr.grammar]) shall appertain to an explicit instantiation.
If the explicit instantiation is for a class or member class, the elaborated-type-specifier in the declaration shall include a simple-template-id; otherwise, the declaration shall be a simple-declaration whose init-declarator-list comprises a single init-declarator that does not have an initializer.
If the explicit instantiation is for a variable template specialization, the unqualified-id in the declarator shall be a simple-template-id.
[Example 1: template<class T> class Array { void mf(); }; template class Array<char>; template void Array<int>::mf(); template<class T> void sort(Array<T>& v) { /* ... */ } template void sort(Array<char>&); // argument is deduced here namespace N { template<class T> void f(T&) { } } template void N::f<int>(int&); — end example]
An explicit instantiation does not introduce a name ([basic.scope.scope]).
A declaration of a function template, a variable template, a member function or static data member of a class template, or a member function template of a class or class template shall be reachable from any explicit instantiation of that entity.
A definition of a class template, a member class of a class template, or a member class template of a class or class template shall be reachable from any explicit instantiation of that entity unless an explicit specialization of the entity with the same template arguments is reachable therefrom.
If the declaration of the explicit instantiation names an implicitly-declared special member function ([special]), the program is ill-formed.
The declaration in an explicit-instantiation and the declaration produced by the corresponding substitution into the templated function, variable, or class are two declarations of the same entity.
[Note 1:
These declarations are required to have matching types as specified in [basic.link], except as specified in [except.spec].
[Example 2: template<typename T> T var = {}; template float var<float>; // OK, instantiated variable has type float template int var<int[16]>[]; // OK, absence of major array bound is permitted template int *var<int>; // error: instantiated variable has type int template<typename T> auto av = T(); template int av<int>; // OK, variable with type int can be redeclared with type auto template<typename T> auto f() {} template void f<int>(); // error: function with deduced return type // redeclared with non-deduced return type ([dcl.spec.auto]) — end example]
— end note]
Despite its syntactic form, the declaration in an explicit-instantiation for a variable is not itself a definition and does not conflict with the definition instantiated by an explicit instantiation definition for that variable.
For a given set of template arguments, if an explicit instantiation of a template appears after a declaration of an explicit specialization for that template, the explicit instantiation has no effect.
Otherwise, for an explicit instantiation definition, the definition of a function template, a variable template, a member function template, or a member function or static data member of a class template shall be present in every translation unit in which it is explicitly instantiated.
A trailing template-argument can be left unspecified in an explicit instantiation of a function template specialization or of a member function template specialization provided it can be deduced ([temp.deduct.decl]).
If all template arguments can be deduced, the empty template argument list <> may be omitted.
[Example 3: template<class T> class Array { /* ... */ }; template<class T> void sort(Array<T>& v) { /* ... */ } // instantiate sort(Array<int>&) -- template-argument deduced template void sort<>(Array<int>&); — end example]
[Note 2:
An explicit instantiation of a constrained template is required to satisfy that template's associated constraints ([temp.constr.decl]).
The satisfaction of constraints is determined when forming the template name of an explicit instantiation in which all template arguments are specified ([temp.names]), or, for explicit instantiations of function templates, during template argument deduction ([temp.deduct.decl]) when one or more trailing template arguments are left unspecified.
— end note]
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 direct non-template members that has not been previously explicitly specialized in the translation unit containing the explicit instantiation, provided that the associated constraints, if any, of that member are satisfied by the template arguments of the explicit instantiation ([temp.constr.decl], [temp.constr.constr]), except as described below.
[Note 3:
In addition, it will typically be an explicit instantiation of certain implementation-dependent data about the class.
— end note]
An explicit instantiation definition that names a class template specialization explicitly instantiates the class template specialization and is an explicit instantiation definition of only those members that have been defined at the point of instantiation.
An explicit instantiation of a prospective destructor ([class.dtor]) shall correspond to the selected destructor of the class.
If an entity is the subject of both an explicit instantiation declaration and an explicit instantiation definition in the same translation unit, the definition shall follow the declaration.
An entity that is the subject of an explicit instantiation declaration and that is also used in a way that would otherwise cause an implicit instantiation in the translation unit shall be the subject of an explicit instantiation definition somewhere in the program; otherwise the program is ill-formed, no diagnostic required.
[Note 4:
This rule does apply to inline functions even though an explicit instantiation declaration of such an entity has no other normative effect.
This is needed to ensure that if the address of an inline function is taken in a translation unit in which the implementation chose to suppress the out-of-line body, another translation unit will supply the body.
— end note]
An explicit instantiation declaration shall not name a specialization of a template with internal linkage.
An explicit instantiation does not constitute a use of a default argument, so default argument instantiation is not done.
[Example 4: char* p = 0; template<class T> T g(T x = &p) { return x; } template int g<int>(int); // OK even though &p isn't an int. — end example]