Справочное руководство по C++

R.9.9 Имена локальных типов.

Имена типов подчиняются точно таким же правилам областей видимости, как и другие имена. В частности, имена типов, определенные в описании класса, нельзя использовать вне этого класса без уточнения, например:

Class X {

Public:

 typedef int I;

 class Y {/*… */}.

 I a;

};

I b; // ошибка.

Y c; // ошибка.

X::Y d; // ошибка.

Следующее положение ограничивает зависимость от контекста правил описания членов класса, а так же правила переноса тела функций, являющихся подстановками. После использования в описании класса имя константы, имя-класса или имя-typedef не может переопределяться в описании этого класса. Имя, не являющееся именем-класса или именем-typedef не может быть определено в описании класса как имя-класса или имя-typedef, если оно уже использовалось иначе в описании этого класса. Рассмотрим пример:

Typedef int c;

Enum { i = 1 };

Class X {

 char v[i];

 int f() { return sizeof(c); }.

 char c; // ошибка: имя typedef.

  // переопределяется после использования.

 enum { i = 2 }; // ошибка: `i' переопределяется после.

  // использования в задании типа `char[i]'.

};

Typedef char* T;

Struct Y {

 T a;

 typedef long T; // ошибка: имя T уже использовано.

 T b;

};