2016-06-10 11 views
7

Может ли этот код быть скомпилирован?Точка создания шаблона класса

#include <iostream> 

template <typename T> 
struct TMPL 
{ 
    using TP = typename T::TP; //is CL::TP visible (with T == CL)? 
}; 

struct CL 
{ 
    using TP = int; 
    TMPL<CL>::TP val; 
}; 

int main() 
{ 
    CL cl; 
} 

TMPL сразу инстанцирован до определения класса CL согласно стандарту 14.6.4.1/4

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

Так, CL :: TP не отображается в точке TMPL экземпляра, но все компиляторы (MSVC, GCC, лязг) скомпилировать его в порядке. Я также нашел отчет о дефекте http://www.open-std.org/jtc1/sc22/wg21/docs/cwg_active.html#287, но он, по-видимому, не был принят

+2

Кроме того, это не было «отклонено». Это «разработка». Если бы это было «отклонено», статус был бы НАД. –

+0

Я прочитал его, но это предложение еще не принято, и код в моем примере не должен компилироваться, так как я думаю – user3514538

+0

Как я уже сказал, 'CL' не является шаблоном. Дефект не относится к нему. Целью дефекта является создание случая, когда 'CL' * является * шаблоном так же, как ваш пример кода. –

ответ

2

Ваш пример не идентичен вашему примеру в defect report. В отчете о дефектах CL является шаблоном класса. Однако цель предлагаемой резолюции сделать случай шаблон такой же, как нешаблонном один, он же [basic.scope.pdecl]:

6 После точки заявления члена класса, имя члена можно посмотреть вверх в рамках своего класса. [Примечание: это значение , даже если класс является неполным классом. Например,

struct X { 
    enum E { z = 16 }; 
    int b[X::z];  // OK 
}; 

- конец примечания]

Тогда предлагаемое решение:

В 14.6.4.1 [temp.point] пункт 3 изменения:

точка инстанцирования непосредственно перед точкой экземпляр окружающего шаблона. В противном случае точка для такой специализации немедленно предшествует объявлению или определению области пространства имен , которое относится к специализации .

Кому:

точки экземпляра является то же в качестве точки конкретизации шаблона вмещающей. В противном случае, точка создания для такой специализации немедленно предшествует . [Примечание. Точка создания экземпляра все еще находится в области пространства имен, но любые объявления, предшествующие точке экземпляра , даже если они не имеют области пространства имен, считаются имеющими .]

Добавить после пункта 3:

Если неявно конкретизируется шаблон класса специализации класса член специализации или специализации шаблона класса ссылки класс, шаблон класса специализации, член класса специализации или специализации шаблона класса, содержащего ссылку специализации , которая прямо или косвенно вызвала экземпляр , требования полноты и упорядочения ссылки на класс применяются в контексте ссылки специализации .

С учетом последних draft, не-шаблонный корпус был и остается в силе. Случай с шаблоном - нет. Однако дефект drafting, что означает, что шаблонный шаблон предназначен для компиляции.

Редакционный: Неформальная был достигнут консенсус в рабочей группе и описывается грубо говоря в Ориентировочное резолюции, хотя точная формулировка для изменения еще не доступны.

+0

Благодарим вас за ответ. Я просто имел в виду случай без шаблонов, где точка инстанцирования помещается перед классом CL и не может видеть членов CL, которые помещаются позже – user3514538

 Смежные вопросы

  • Нет связанных вопросов^_^