In C++, I'd like to use a nested class inside a templated class as template template parameter. For non-nested classes the pattern is:
template<class T>
class A {
public:
T a;
// ...
};
template<class T, template<class ST> class S>
class B {
public:
S<T> b;
// ...
};
B<int, A> b;
Now I'd like to add a nested class to A
and use this nested class as template template parameter S
of class B
, like this:
template<class T>
class A {
public:
class AA {
public:
T aa;
// ...
};
// ...
};
template<class T, template<class ST> class S>
class B {
public:
S<T> b;
// ...
};
B<int, A> b1; // ok
B<int, A::AA> b2; // error
B<int, A<int>::AA> b3; // error
I understand that the declarations of b2
and b3
are errors because A::AA
is incomplete and A<int>::AA
is not a template.
I would like to be able to declare something similar to b2
. The idea is that A
and B
should both use the same class T
.
I would like to be able to declare a number of classes similar to A
with individually named sub-classes. Another use of this I can think of are multiple sub-classes of A
that can be used as template template parameter to B
.
One workaround I see is to refrain from using individual names on the sub-classes of A
, use the b1
declaration (use A
as template template parameter S
for B
) and change the implementation of B
accordingly (i.e. use S::AA<T>
instead of S<T>
):
template<class T, template<class ST> class S>
class B {
public:
S::AA<T> b;
// ...
};
B<int, A> b;
The other workaround I see is to reduce the template template parameter of class B
to a simple template parameter, and ensure the same T
by other means.
Is there some other possibility? If yes, how?
Edit: Added forgotten class
in template
for B
and changed template template parameter name to ST
.
This works for me:
template<class T>
class A {
public:
class AA {
public:
T aa;
// ...
};
// ...
};
template<class T, template<class ST> class S >
class B {
public:
S<T> b;
// ...
};
template<class T> using NestedAA = typename A<T>::AA;
int main()
{
B<int, NestedAA> b; // ok
return 0;
}
If for any reason you are constrained to C++03, type aliases won't be available to you. You can then replace the "using" statement with the following definition for NestedAA:
template<class T>
class NestedAA : public A<T>::AA
{
};
You may create an template alias:
template <typename T>
using innerAA = typename A<T>::AA;
and then
B<int, innerAA> b42;
Demo
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With