template-declaration, В котором declarationэто alias-declarationобъявляет identifierбыть alias template. Шаблон псевдонима - это имя семейства типов. Имя шаблона псевдонима - template-name.
Когда template-idотносится к специализации шаблона псевдонима, это равносильно тому , ассоциированному типа , полученный путем замены сва template-arguments для template-parameters в type-idшаблоне псевдонима. [ Note: Имя шаблона псевдонима никогда не выводится. ] [ — end note Example:
template<class T> struct Alloc { /* ... */ }; template<class T> using Vec = vector<T, Alloc<T>>; Vec<int> v; // same as vector<int, Alloc<int>> v; template<class T> void process(Vec<T>& v) { /* ... */ } template<class T> void process(vector<T, Alloc<T>>& w) { /* ... */ } // error: redefinition template<template<class> class TT> void f(TT<int>); f(v); // error: Vec not deduced template<template<class,class> class TT> void g(TT<int, Alloc<int>>); g(v); // OK: TT = vector
— end example ]
Однако, если template-idэто зависит, последующая подстановка аргументов шаблона по-прежнему применяется к template-id. [ Example:
template<typename...> using void_t = void;
template<typename T> void_t<typename T::foo> f();
f<int>(); // error, int does not have a nested type foo
— end example ]
В type-idобъявлении шаблона псевдонима не должно быть ссылки на объявляемый шаблон псевдонима. Тип, созданный специализацией шаблона псевдонима, не должен прямо или косвенно использовать эту специализацию. [ Example:
template <class T> struct A;
template <class T> using B = typename A<T>::U;
template <class T> struct A {
typedef B<T> U;
};
B<short> b; // error: instantiation of B<short> uses own type via A<short>::U
— end example ]