Sidar
Sidar

Reputation: 534

C++ function : Variadic templates with no arguments

I am not sure if this question is already answered. But here it goes:

I was wondering if it's possible to do something like

template<typename...classes>
void createObject(){

  //pass each type into my template function wich takes one type only.

}

I'm really not getting how it exactly works. The reason I can't provide any function arguments is because my template function which should be called within the method only takes one type. This is because it returns an object depending on it's type.

Any suggestion?

Note: GCC 4.6.2

Upvotes: 6

Views: 8259

Answers (2)

mitchnull
mitchnull

Reputation: 6331

One way is to use the following function to expand the calls:

template <typename... Ts>
void swallow(Ts&&...) {
}

I'll assume you want to call the following function:

template <typename T>
void create() {
}

In this case, you'll need a helper function that converts the void create to one that returns something, so that we can expand it in the arg-list of swallow (if your create function is already non-void, then this extra step is not necessary):

template <typename T>
int createHelper() {
    create<T>();
    return 0;
}

template<typename... Ts>
void createObject(){
    swallow(createHelper<Ts>()...);
}

Edit: instead of the createHelper, we could use a trick with the comma operator:

swallow((create(), 0)...);

Upvotes: 3

Sarfaraz Nawaz
Sarfaraz Nawaz

Reputation: 361254

template<typename...>
struct caller;

template<typename T, typename...Rest>
struct caller<T, Rest...>
{
     static void call()
     {
        create<T>();
        caller<Rest...>::call();
     }
};

template<>
struct caller<>
{
     static void call()
     {
     }
};

//since you've not mentioned the return type, I'm assuming it to be void
//if it is not void, then I don't know what you're going to return, and HOW!   
template<typename...classes>
void createObject(){
      caller<classes...>::call();
}

Demo : http://ideone.com/UHY8n


Alternative (a shorter version):

template<typename...>
struct typelist{};

template<typename T, typename ... Rest>
void call(typelist<T,Rest...>)
{
  create<T>();
  call(typelist<Rest...>());
};

void call(typelist<>) { }

template<typename...classes>
void createObject(){
      call(typelist<classes...>());
}

Demo : http://ideone.com/cuhBh

Upvotes: 4

Related Questions