Использование typedef и typename внутри шаблона - PullRequest
4 голосов
/ 12 декабря 2011

Я хочу определить имя типа в шаблонном классе, который я могу использовать в другом месте для ссылки на тип члена в классе.

template <class T>
class CA
{
public:
    //typedef typename T::iterator iterator_type;
    typedef typename T ElementType1; // compile error on this line
    //typedef T ElementType2;

    T m_element;
};

и используйте его так:

template <class T>
class CDerived : public CBase<typename T::ElementType1>
{
 //...
};

и объявлять объекты как:

typedef CDerived<CA> MyNewClass;

Разве это не возможно? У меня есть код, который правильно компилируется под VS2010, но не под Xcode, который использует строку:

typedef typename T ElementType1;

Видимо, компилятор ожидает квалифицированное имя после typename, но я не вижу, как оно может быть для типа шаблона.

Я не понимаю разницу между ElementType1 и ElementType2 в этом контексте.

Я посмотрел на многие вопросы о переполнении стека, но большинство, похоже, ссылались только на тот тип объявлений, как iterator_type в моем примере.

Ответы [ 2 ]

4 голосов
/ 12 декабря 2011

typename может использоваться только для определения квалифицированного имени;оно не применяет имя, следующее сразу после него, но к определенному имени, то есть в:

typedef typename T::X x;

typename применяется к X, а не к T.По этой причине, это только законно (в этом использовании) перед квалифицированными именами.Неквалифицированные имена должны находиться в контексте, где компилятор может знать, является ли имя типом или нет.(На практике это проблема только типов, определенных в зависимом базовом классе, и их можно квалифицировать.)

4 голосов
/ 12 декабря 2011

Компилятор уже знает, T - это тип (class T), поэтому в первом случае вам не нужен квалификатор typename. ОТО, компилятор не знает заранее, что T::ElementType1 это тип; это зависит от того, что Т в конечном итоге.

...