Suppose we have code:
template <int Size>
struct A {
template <typename T, typename Enable = void> struct B;
template <> struct B<bool, std::enable_if_t<Size >= 1>> {};
template <> struct B<short, std::enable_if_t<Size >= 2>> {};
};
template <int Size>
struct D {
template <typename T> struct E;
template <> struct E<bool> {};
template <> struct E<short> {};
};
template <int Size>
struct F {
template <typename T> struct G {};
};
template <int Size, typename T, typename Enable = void> struct C;
template <int Size> struct C<Size, bool, std::enable_if_t<Size >= 1>> {};
template <int Size> struct C<Size, short, std::enable_if_t<Size >= 2>> {};
Structs C and F compile well in all of CLang/GCC/MSVC. Struct D compiles well in CLang/MSVC, but has compile error in GCC. Struct A doesn't compile by all of CLang/GCC/MSVC.
GCC's error for D (similar for A):
<source>:19:15: error: explicit specialization in non-namespace scope 'struct D<Size>'
19 | template <> struct E<bool> {};
CLang's error for A:
type_traits:2514:44: error: no type named 'type' in 'std::enable_if<false>'; 'enable_if' cannot be used to disable this declaration
using enable_if_t = typename enable_if<_Cond, _Tp>::type;
MSVC's error for A:
<source>(11): error C2938: 'std::enable_if_t<false,void>' : Failed to specialize alias template
<source>(11): note: see reference to alias template instantiation 'std::enable_if_t<false,void>' being compiled
<source>(30): note: see reference to class template instantiation 'A<1>' being compiled
<source>(11): error C2913: explicit specialization; 'A<1>::B' is not a specialization of a class template
I have several questions:
Is it at all allowed in std C++ to SPECIALIZE templated sub-class? What are the limitations? Looks like GCC doesn't allow at all and CLang/MSVC allow but with certain limits.
Is it at all allowed to HAVE templated sub-class. If allowed then how do I specialize it? Maybe some out-of-class specialization is allowed for them (then what's the syntax)?
If not allowed to specialize templated sub-class then at least is it allowed to have fully-defined templated sub-class (without specializations)? Looks like struct F above uses fully-defined templated sub-class and compiles well everywhere.