There are three forms of template-argument, corresponding to the three forms of template-parameter: type, non-type and template. The type and form of each template-argument specified in a template-id shall match the type and form specified for the corresponding parameter declared by the template in its template-parameter-list. When the parameter declared by the template is a template parameter pack ([temp.variadic]), it will correspond to zero or more template-arguments. [ Example:
template<class T> class Array {
  T* v;
  int sz;
public:
  explicit Array(int);
  T& operator[](int);
  T& elem(int i) { return v[i]; }
};
Array<int> v1(20);
typedef std::complex<double> dcomplex;  // std::complex is a standard
                                        // library template
Array<dcomplex> v2(30);
Array<dcomplex> v3(40);
void bar() {
  v1[3] = 7;
  v2[3] = v3.elem(4) = dcomplex(7,8);
}
— end example ]
In a template-argument, an ambiguity between a type-id and an expression is resolved to a type-id, regardless of the form of the corresponding template-parameter.139 [ Example:
template<class T> void f();
template<int I> void f();
void g() {
  f<int()>();       // int() is a type-id: call the first f()
}
— end example ]
The name of a template-argument shall be accessible at the point where it is used as a template-argument. [ Note: If the name of the template-argument is accessible at the point where it is used as a template-argument, there is no further access restriction in the resulting instantiation where the corresponding template-parameter name is used. — end note ] [ Example:
template<class T> class X {
  static T t;
};
class Y {
private:
  struct S { /* ... */ };
  X<S> x;           // OK: S is accessible
                    // X<Y::S> has a static member of type Y::S
                    // OK: even though Y::S is private
};
X<Y::S> y;          // error: S not accessible
— end example ] For a template-argument that is a class type or a class template, the template definition has no special access rights to the members of the template-argument. [ Example:
template <template <class TT> class T> class A {
  typename T<int>::S s;
};
template <class U> class B {
private:
  struct S { /* ... */ };
};
A<B> b;             // ill-formed: A has no access to B::S
— end example ]
When template argument packs or default template-arguments are used, a template-argument list can be empty. In that case the empty <> brackets shall still be used as the template-argument-list. [ Example:
template<class T = char> class String; String<>* p; // OK: String<char> String* q; // syntax error template<class ... Elements> class Tuple; Tuple<>* t; // OK: Elements is empty Tuple* u; // syntax error
— end example ]
An explicit destructor call ([class.dtor]) for an object that has a type that is a class template specialization may explicitly specify the template-arguments. [ Example:
template<class T> struct A {
  ~A();
};
void f(A<int>* p, A<int>* q) {
  p->A<int>::~A();              // OK: destructor call
  q->A<int>::~A<int>();         // OK: destructor call
}
— end example ]
If the use of a template-argument gives rise to an ill-formed construct in the instantiation of a template specialization, the program is ill-formed.
When the template in a template-id is an overloaded function template, both non-template functions in the overload set and function templates in the overload set for which the template-arguments do not match the template-parameters are ignored. If none of the function templates have matching template-parameters, the program is ill-formed.
A template-argument followed by an ellipsis is a pack expansion ([temp.variadic]).
There is no such ambiguity in a default template-argument because the form of the template-parameter determines the allowable forms of the template-argument.
A template-argument for a template-parameter which is a type shall be a type-id.
[ Example:
template <class T> class X { };
template <class T> void f(T t) { }
struct { } unnamed_obj;
void f() {
  struct A { };
  enum { e1 };
  typedef struct { } B;
  B b;
  X<A> x1;          // OK
  X<A*> x2;         // OK
  X<B> x3;          // OK
  f(e1);            // OK
  f(unnamed_obj);   // OK
  f(b);             // OK
}
— end example ] [ Note: A template type argument may be an incomplete type ([basic.types]). — end note ]
If a declaration acquires a function type through a type dependent on a template-parameter and this causes a declaration that does not use the syntactic form of a function declarator to have function type, the program is ill-formed. [ Example:
template<class T> struct A {
  static T t;
};
typedef int function();
A<function> a;                  // ill-formed: would declare A<function>::t
                                // as a static member function
— end example ]
A template-argument for a non-type, non-template template-parameter shall be one of:
for a non-type template-parameter of integral or enumeration type, a converted constant expression ([expr.const]) of the type of the template-parameter; or
the name of a non-type template-parameter; or
a constant expression ([expr.const]) that designates the address of a complete object with static storage duration and external or internal linkage or a function with external or internal linkage, including function templates and function template-ids but excluding non-static class members, expressed (ignoring parentheses) as & id-expression, where the id-expression is the name of an object or function, except that the & may be omitted if the name refers to a function or array and shall be omitted if the corresponding template-parameter is a reference; or
a constant expression that evaluates to a null pointer value ([conv.ptr]); or
a constant expression that evaluates to a null member pointer value ([conv.mem]); or
a pointer to member expressed as described in [expr.unary.op]; or
a constant expression of type std::nullptr_t.
[ Note: A string literal ([lex.string]) does not satisfy the requirements of any of these categories and thus is not an acceptable template-argument. [ Example:
template<class T, const char* p> class X {
  /* ... */
};
X<int, "Studebaker"> x1;        // error: string literal as template-argument
const char p[] = "Vivisectionist";
X<int,p> x2;                    // OK
— end example ] — end note ]
[ Note: Addresses of array elements and names or addresses of non-static class members are not acceptable template-arguments. [ Example:
template<int* p> class X { };
int a[10];
struct S { int m; static int s; } s;
X<&a[2]> x3;                    // error: address of array element
X<&s.m> x4;                     // error: address of non-static member
X<&s.s> x5;                     // error: &S::s must be used
X<&S::s> x6;                    // OK: address of static member
— end example ] — end note ]
[ Note: Temporaries, unnamed lvalues, and named lvalues with no linkage are not acceptable template-arguments when the corresponding template-parameter has reference type. [ Example:
template<const int& CRI> struct B { /* ... */ };
B<1> b2;                        // error: temporary would be required for template argument
int c = 1;
B<c> b1;                        // OK
— end example ] — end note ]
The following conversions are performed on each expression used as a non-type template-argument. If a non-type template-argument cannot be converted to the type of the corresponding template-parameter then the program is ill-formed.
For a non-type template-parameter of integral or enumeration type, conversions permitted in a converted constant expression ([expr.const]) are applied.
for a non-type template-parameter of type pointer to object, qualification conversions ([conv.qual]) and the array-to-pointer conversion ([conv.array]) are applied; if the template-argument is of type std::nullptr_t, the null pointer conversion ([conv.ptr]) is applied. [ Note: In particular, neither the null pointer conversion for a zero-valued integer literal ([conv.ptr]) nor the derived-to-base conversion ([conv.ptr]) are applied. Although 0 is a valid template-argument for a non-type template-parameter of integral type, it is not a valid template-argument for a non-type template-parameter of pointer type. However, both (int*)0 and nullptr are valid template-arguments for a non-type template-parameter of type “pointer to int.” — end note ]
For a non-type template-parameter of type reference to object, no conversions apply. The type referred to by the reference may be more cv-qualified than the (otherwise identical) type of the template-argument. The template-parameter is bound directly to the template-argument, which shall be an lvalue.
For a non-type template-parameter of type pointer to function, the function-to-pointer conversion ([conv.func]) is applied; if the template-argument is of type std::nullptr_t, the null pointer conversion ([conv.ptr]) is applied. If the template-argument represents a set of overloaded functions (or a pointer to such), the matching function is selected from the set ([over.over]).
For a non-type template-parameter of type reference to function, no conversions apply. If the template-argument represents a set of overloaded functions, the matching function is selected from the set ([over.over]).
For a non-type template-parameter of type pointer to member function, if the template-argument is of type std::nullptr_t, the null member pointer conversion ([conv.mem]) is applied; otherwise, no conversions apply. If the template-argument represents a set of overloaded member functions, the matching member function is selected from the set ([over.over]).
For a non-type template-parameter of type pointer to data member, qualification conversions ([conv.qual]) are applied; if the template-argument is of type std::nullptr_t, the null member pointer conversion ([conv.mem]) is applied.
[ Example:
template<const int* pci> struct X { /* ... */ };
int ai[10];
X<ai> xi;                       // array to pointer and qualification conversions
struct Y { /* ... */ };
template<const Y& b> struct Z { /* ... */ };
Y y;
Z<y> z;                         // no conversion, but note extra cv-qualification
template<int (&pa)[5]> struct W { /* ... */ };
int b[5];
W<b> w;                         // no conversion
void f(char);
void f(int);
template<void (*pf)(int)> struct A { /* ... */ };
A<&f> a;                        // selects f(int)
— end example ]
A template-argument for a template template-parameter shall be the name of a class template or an alias template, expressed as id-expression. When the template-argument names a class template, only primary class templates are considered when matching the template template argument with the corresponding parameter; partial specializations are not considered even if their parameter lists match that of the template template parameter.
Any partial specializations ([temp.class.spec]) associated with the primary class template or primary variable template are considered when a specialization based on the template template-parameter is instantiated. If a specialization is not visible at the point of instantiation, and it would have been selected had it been visible, the program is ill-formed; no diagnostic is required. [ Example:
template<class T> class A {     // primary template
  int x;
};
template<class T> class A<T*> { // partial specialization
  long x;
};
template<template<class U> class V> class C {
  V<int>  y;
  V<int*> z;
};
C<A> c;                         // V<int> within C<A> uses the primary template,
                                // so c.y.x has type int
                                // V<int*> within C<A> uses the partial specialization,
                                // so c.z.x has type long
— end example ]
A template-argument matches a template template-parameter (call it P) when each of the template parameters in the template-parameter-list of the template-argument's corresponding class template or alias template (call it A) matches the corresponding template parameter in the template-parameter-list of P. Two template parameters match if they are of the same kind (type, non-type, template), for non-type template-parameters, their types are equivalent ([temp.over.link]), and for template template-parameters, each of their corresponding template-parameters matches, recursively. When P's template-parameter-list contains a template parameter pack ([temp.variadic]), the template parameter pack will match zero or more template parameters or template parameter packs in the template-parameter-list of A with the same type and form as the template parameter pack in P (ignoring whether those template parameters are template parameter packs).
[ Example:
template<class T> class A { /* ... */ };
template<class T, class U = T> class B { /* ... */ };
template <class ... Types> class C { /* ... */ };
template<template<class> class P> class X { /* ... */ };
template<template<class ...> class Q> class Y { /* ... */ };
X<A> xa;            // OK
X<B> xb;            // ill-formed: default arguments for the parameters of a template argument are ignored
X<C> xc;            // ill-formed: a template parameter pack does not match a template parameter
Y<A> ya;            // OK
Y<B> yb;            // OK
Y<C> yc;            // OK
— end example ]
[ Example:
template <class T> struct eval;
template <template <class, class...> class TT, class T1, class... Rest>
struct eval<TT<T1, Rest...>> { };
template <class T1> struct A;
template <class T1, class T2> struct B;
template <int N> struct C;
template <class T1, int N> struct D;
template <class T1, class T2, int N = 17> struct E;
eval<A<int>> eA;                // OK: matches partial specialization of eval
eval<B<int, float>> eB;         // OK: matches partial specialization of eval
eval<C<17>> eC;                 // error: C does not match TT in partial specialization
eval<D<int, 17>> eD;            // error: D does not match TT in partial specialization
eval<E<int, float>> eE;         // error: E does not match TT in partial specialization
— end example ]