Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Variadic Template in template class

81 views
Skip to first unread message

Laurent

unread,
Oct 27, 2014, 8:56:06 AM10/27/14
to
Hi,
I try to understand the variadic templates but I can't compile the following example... Any hints ? (g++ 4.4 and g++ 4.7)

template <int LEVEL>
struct Toto{

Toto<LEVEL-1> subToto_;

template <typename First, typename... Rest>
Toto(const First & first, const Rest & rest):subToto_(rest){
}
};

template <>
struct Toto<1>{

template <class T>
Toto(const T & t){
}
};

int main () {
Toto<3> toto(1,2,3);
}

I have the following error :

testArray.cxx:52:46: erreur: parameter packs not expanded with '...':
testArray.cxx:52:46: note: 'Rest'

Laurent

Victor Bazarov

unread,
Oct 27, 2014, 11:07:40 AM10/27/14
to
I think you need a slightly different syntax. You can't use 'Rest' as
if it is a single type. It's a "parameter pack", which needs the
expansion syntax, something like

template<typename First, typename... Rest>
Toto(const First& first, Rest...) : subToto_(Rest...) {}

V
--
I do not respond to top-posted replies, please don't ask

Laurent

unread,
Oct 27, 2014, 12:19:08 PM10/27/14
to
Thanx, the following syntax do compile :

template <typename First, typename... Rest>
Toto(const First & first, const Rest&... rest):subToto_(rest...){}

Juha Nieminen

unread,
Oct 30, 2014, 8:31:27 AM10/30/14
to
Laurent <laurent...@gmail.com> wrote:
> Thanx, the following syntax do compile :
>
> template <typename First, typename... Rest>
> Toto(const First & first, const Rest&... rest):subToto_(rest...){}

In general, the ... syntax for variadic templates goes like this:

In the template declaration you use "typename... [name]" to indicate
a variable amount of parameters. (Could also be "[type]... [name]",
eg "int... Values", but that's besides the point.)

Then wherever you are going to use the typename [name], you use
the entire type expression and append "..." to it.

For example "const Rest&..." means that each of the types will be
expanded as "const [the specified type]&".

The place where you use the actual parameter, you can write any
expression you want, and append "..." to it, which means that the
expression will be repeated for each of the specified types, separated
by commas. In other words, something like this is completely valid:

template<typename... T>
void foo(const T&... parameters)
{
int results[] = { someFunction(parameters)... };
}

Notice that "someFunction(parameters...)" would be different from
"someFunction(parameters)...". The former means that all the parameters
are given to the single function call (which must of course support
being given a variable number of parameters), while the latter means
that a "someFunction()" call will be created for each parameter (in
other words, said function just takes one parameter), and all these
calls basically separated with commas.

--- news://freenews.netfront.net/ - complaints: ne...@netfront.net ---

Laurent

unread,
Nov 7, 2014, 2:12:14 AM11/7/14
to
Thank you very much for your detailed explanation. The last example showing how to apply a given function to all the parameters matches exactly my current need !
I wonder if I can use the result as a variadic argument for another function
anotherFunction(someFunction(parameters)...)
I will try this.
Thank you again !
Laurent

Juha Nieminen

unread,
Nov 7, 2014, 9:54:01 AM11/7/14
to
Laurent <laurent...@gmail.com> wrote:
> I wonder if I can use the result as a variadic argument for another function
> anotherFunction(someFunction(parameters)...)

That means that it, roughtly speaking, gets expaned to:

anotherFunction(someFunction(param1), someFunction(param2), (etc))

In other words, 'anotherFunction' needs to be able to take a variable
number of parameters of the return value type of 'someFunction'.

(Note that it is possible to restrict the number of parameters given
to a variadic template, which can sometimes be useful. This happens
by writing a static_assert inside the template where you check that
sizeof...(parameters) is within the limits you want.)

Laurent

unread,
Nov 8, 2014, 3:05:57 AM11/8/14
to
Thank you so very much ! I have tried this yesterday in order to write a small library that deals with multidim array (on top of Eigen and TBB) that allow automatic vectorization (and parallelization) of algorithms. The basic idea is to handle proper interweaving of the underlying array containers in order to vectorize loops that do not match the inner dimension of arrays...

The variadic template feature is so cool and I was so excited about this that I spent a signicative amount of my day in disturbing my collegues showing (off) the few lines of codes I wrote ;). Something like

vector_for_each(user_algo(),arrays...))
can be written as for_each(user_algo(),(arrays.getSIMDView())...) //methods!

C++ new stuff enables real functional approach ! With type classes it would be perfect ;)

Thank you gain !
Laurent

0 new messages