Boost logo

Boost :

From: Andrei Alexandrescu (andrewalex_at_[hidden])
Date: 2001-11-21 01:52:53


> Here's the definition of make_list:
> http://www.lambdasoft.dk/comet/doc/typelist_8h-source.html
>
> What's wrong with this approach? Is it failing on point #2?

It looks like you can call make_list with at most 40 arguments. It's true
that yo might never need more, and if you do, you can use append.

I don't know. I'd love to deprecate the TYPELIST_nn macros, but a truly
elegant solution would be the language to support variadic arguments in
templates. This feature, if also applicable to functions, would make a lot
of library code that people wrote (Loki::Functor, Loki::Variant, ScopeGuard
come to mind) really small and nice, and would render true our dreams of a
typesafe printf equivalent.

More concretely, I am thinking of something that allows the programmer to
progressively reduce a template's number of arguments through
specialization:

// Declare a class template that can take any number of parameters
template <typename[] Ts> class Widget;

// Specializations that kick in

// For one argument only
template <typename T>
class Widget
{
    ...
};

// For more than one argument
template <typename T, typename[] Ts>
class Widget : public Widget<T>, public Widget<Ts>
{
    ...
};

When you instantiate Widget<int, double, float>, first the second
specialization kicks in with int as T and (double, float) as Ts. Then,
Widget<int> is instantiated (first specialization kicks in) and
Widget<double, float> is instantiated, which in turn instantiates
Widget<double> and Widget<float>.

For functions, a possible syntax would be:

// Declare a safe vararg function
template <typename[] Ts> void Printf(const char*, Ts);

You cannot use the second argument directly if it is in the form typename[],
but you can "consume" the number of arguments one at a time through
overloads and/or specializations (this part is unclear to me):

// Declare a safe vararg function
template <typename[] Ts>
void Printf(const char*, int, Ts);

// Another one
template <typename[] Ts>
void Printf(const char*, double, Ts);

and so on. I guess such a facility, although not too rich, would be enough.

Well if you have the above, you can implement VERY easily and very
elegantly:

* Typelists (or would they be type vectors?)
* Tuples
* Functors
* Factories
* Visitors
* Variants
* Typesafe variadic utility fns such as
    => printf
    => min/max with multiple args, etc.
    => smart constructors "create a vector containing 1, 2, 3, 4, and 5"
* many others

Andrei


Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk