Я просто столкнулся с странной разницей в поведении между clang и gcc, где я хотел скомпилировать код, который выглядит примерно так:
namespace n1 {
template <class T1, class T2>
struct MyTemplate {
struct Inner {};
};
}
using namespace n1;
namespace n2 {
using MyClass = MyTemplate<int, int>;
}
namespace n1 {
using n2::MyClass;
template<> struct MyClass::Inner {
int member;
};
MyClass::Inner inner{0};
}
Клан счастливо компилирует это:
$ clang++ -std=c++11 -c -o alias_specialization.o alias_specialization.cc
но gcc вызывает следующую ошибку:
$ g++ -std=c++11 -c -o alias_specialization.o alias_specialization.cc
alias_specialization:15:30: error: declaration of ‘struct n1::MyTemplate<int, int>::Inner’ in namespace ‘n1’ which does not enclose ‘using MyClass = struct n1::MyTemplate<int, int>’
template<> struct MyClass::Inner {
Я знаю, что могу просто написать полное имя исходного типа (MyTemplate<int, int>
) вместо MyClass
в строке 15.
Но мне просто интересно, какой из двух компиляторов "прав".
Точные компиляторы используются:
$ clang++ --version
clang version 4.0.0
$ g++ --version
g++ (GCC) 6.3.1 20170306