Reputation: 7262
I have two templates, one is passed to the other as an argument. I would like to be able to use the Args from the argument in the main template. Or if I have:
template <typename T, typename... Args>
class Foo
{
typedef T Type;
static void foo(Args... args)
{
}
};
template <typename C>
class Bar
{
void bar(Args... args)
{
// do something
C::foo(args...);
}
};
How I can make Args
visible in the template Bar
. Note that with typedef T Type
, I can use C::Type
in Bar
. What is the syntax if possible for the variadic argument?
Upvotes: 2
Views: 143
Reputation: 50568
Here a possible solution based on template template parameter:
template<typename T>
class Bar;
template <template<typename...> class C, typename... Args>
class Bar<C<Args...>> {
void bar(Args... args) {
// do something
C<Args...>::foo(args...);
}
};
You can use it as it follows:
Bar<Foo<int, double>> v;
You don't get the arguments Args
directly from the C
class. Instead, the idea is to exploit the fact that the C
class is a variadic templated one for itself, thus getting Args
from the parameter list of a template specialization of Bar
.
Upvotes: 4
Reputation: 88225
You could have a typedef for a 'type list' that wraps Args...
. Here's an example using tuple
to perform the role of the type list:
#include <tuple>
#include <experimental/tuple>
template <typename T, typename... Args>
class Foo
{
public:
using Type = T;
using Arguments = std::tuple<Args...>;
static void foo(Args... args)
{
}
};
template <typename C>
class Bar
{
public:
void bar(typename C::Arguments &&args)
{
// do something
std::experimental::apply(C::foo, args);
}
};
int main() {
Bar<Foo<int, double, float>> b;
b.bar(std::make_tuple(2.0, 1.0f));
}
With a bit more meta-programming it should be possible to produce a Bar::bar
function that takes arguments directly based on C::Arguments
.
Upvotes: 1