6 Basic concepts [basic]

6.3 Scope [basic.scope]

6.3.9 Template parameter scope [basic.scope.temp]

Декларативная область имени параметра шаблона шаблона template-parameter- наименьшая, template-parameter-list в которой имя было введено.

Декларативная область имени параметра шаблона шаблона - наименьшая, template-declarationв которой имя было введено. К этой декларативной области принадлежат только имена параметров шаблона; любой другой вид имени, введенный с помощью declarationa template-declaration, вместо этого вводится в ту же декларативную область, где он был бы введен в результате нешаблонного объявления с тем же именем. [Example:

namespace N {
  template<class T> struct A { };               // #1
  template<class U> void f(U) { }               // #2
  struct B {
    template<class V> friend int g(struct C*);  // #3
  };
}

Декларативная область T, U и V являются template-declarations по линиям # 1, # 2 и # 3, соответственно. Но имена A, f, g и C все они принадлежат к одной и той же декларативной области , а именно - namespace-bodyиз N. (g по-прежнему считается принадлежащей этой декларативной области, несмотря на то, что она была скрыта во время поиска квалифицированного и неквалифицированного имени.) ]end example

Потенциальная область действия имени параметра шаблона начинается с его point of declaration и заканчивается в конце его декларативной области. [ Note: Это означает, что a template-parameterможет использоваться в объявлении последующих template-parameters аргументов и их аргументов по умолчанию, но не может использоваться в предшествующих template-parameters аргументах или их аргументах по умолчанию. Например,

template<class T, T* p, class U = T> class X { /* ... */ };
template<class T> void f(T* p = new T);

Это также означает, что a template-parameterможет использоваться в спецификации базовых классов. Например,

template<class T> class X : public Array<T> { /* ... */ };
template<class T> class Y : public T { /* ... */ };

Использование параметра шаблона в качестве базового класса подразумевает, что класс, используемый в качестве аргумента шаблона, должен быть определен, а не просто объявлен при создании экземпляра шаблона класса. ]end note

Декларативная область имени параметра шаблона вложена в непосредственно включающую декларативную область. [ Note: В результате template-parameter hides любой объект с тем же именем во включающей области. [Example:

typedef int N;
template<N X, typename N, template<N Y> class T> struct A;

Здесь, X является параметром шаблона не-типа типа int и Y является параметром шаблона не-типа того же типа в качестве второго параметра шаблона из A. ] ] end example end note

[ Note: Поскольку имя параметра шаблона не может быть повторно объявлено в пределах его потенциальной области ([temp.local]), область действия параметра шаблона часто является его потенциальной областью. Однако имя параметра шаблона все еще можно скрыть; см [temp.local]. ] end note