Здесь очень интересный фрагмент кода. Я создал его с единственной целью — продемонстрировать поведение компилятора xlC.
namespace ns {
template<typename T> inline T f() { return T(); }
template<> inline double f<double>() { return 0.001; } // test specialization
};
template<typename T >
class A1 {
public: A1( const T& arg = ns::f<T>() ) {};
};
template<typename T>
class D1 {
public: D1(T t = 0) : t_(t) {};
private: T t_;
};
class my {
A1< D1<int> > a;
public: my() ;
};
//namespace ns { template<> D1<int> f<D1<int> >() { return D1<int>(); } }
my::my() { };
void ff() {
my m;
A1<double> ad;
}
Если вы скомпилируете этот код как есть, это вызовет ошибку компиляции:
!$ xlC -c b.cpp
"b.cpp", line 7.40: 1540-0253 (S) This use of undefined class "D1<int>" is not valid.
"b.cpp", line 22.10: 1540-1205 (I) The error occurred while converting to parameter 1 of "A1<D1<int> >::A1(const D1<int> &)".
!$ xlC -qversion
IBM XL C/C++ for AIX, V12.1 (5765-J02, 5725-C72)
!$ uname -a
AIX build25 1 6 00C8B3424C00 powerpc AIX
И теперь, если мы раскомментируем строку, начинающуюся с "//namespace" (что не что иное, как специализация шаблона для имени типа D1‹ int>), ошибка компилятора исчезнет.
У компилятора Gnu, похоже, нет проблем с этим. У кого-нибудь из вас есть идея?
PS. Проблема была найдена конечно же в реальном проекте и это просто упрощенный пример. В реальном проекте существуют сотни классов, таких как D1‹ int>. Предполагается, что они работают из коробки. Но для xlC приходится писать специализированные функции для каждого конкретного случая. Это очень больно...