Boost logo

Boost :

From: David Abrahams (dave_at_[hidden])
Date: 2004-11-17 18:56:53


"Vesa Karvonen" <vesa_karvonen_at_[hidden]> writes:

> David Abrahams
>>Terje Slettebø:
>>
>> >> Yes, that is exactly what I mean above. *Systematic* use of lazy
>> >> template metaprogramming would yield the following (unoptimized)
>> >> factorial function:
>> >>
>> >> template<class n>
>> >> struct FACT
>> >> : IF<IS_0<n>,
>> >> INT<0>,
>> >> TIMES<n, FACT<PRED<n> > > > {};
>> >
>> > Elegant, indeed.
>>
>>But it doesn't work ;-)
>
> Yes, the code snippets in my message have several typos. Like I
> recall seeing certain B.S. saying in a USENET posting, I don't
> (always) compile my e-mails. :)
>
> However, I have written a complete walkthrough of the factorial
> example that you can find in the library I just updated:
>
> http://groups.yahoo.com/group/boost/files/LazyMPL/
>
> [...]
>>In fact it would look almost the same in MPL, though ;-)
>>
>> template<class n>
>> struct fact
>> : if_<equal_to<n, int_<0> >,
>> int_<1>, // <== here's the fix ;-)
>> multiplies<n, fact<typename prior<n>::type> > > {};
>
> Yes, I realize that MPL contains *lots* of "glue" to make Strict TMP
> (strict template metaprogramming) as pleasant as possible.
>
> However, are you sure that the above works? It seems to me that you
> are missing at least an invocation... ;--)

Heh, you're right ;-). Needs eval_if (nee apply if). Lazy is much
nicer.

>>The one typename appears there because prior can work on iterators as
>>well as numeric types. We can kill it this way:
>>
>> template<class n>
>> struct fact
>> : if_<equal_to<n, int_<0> >,
>> int_<1>,
>> multiplies<n, fact<minus<n, int_<1> > > > > {};
>>
>>And this particular case is especially friendly to MPL.
> ^^^^^^^^^^^^^^^^^^^^^^^^^^
>>Some of those advantages are lost when you're not manipulating
>>numeric values.
>
> I'm not sure what mean here. Please elaborate.

I mean that MPL doesn't do nearly as well as this, syntactically, on
examples that don't involve numeric computation. You can always make
a metafunction that always returns an integral constant wrapper look
like an integral constant wrapper itself, which makes factorial
favorable to MPL.

>>This FACT isn't generic (doesn't work for LONG<3>, for example; I
>>assume you have LONG).
>
> No. The library only has the INT-template, whose template argument
> is a long. Designing a complete numeric tower hasn't been a priority
> so far. (Actually, I think that supporting several primitive integer
> types may be an unnecessary overkill anyway

I always wondered about that myself.

> but this is something I have no interest to discuss at this
> point. It would be a red-herring, IMO. The issue is orthogonal to
> the issues of Lazy TMP vs Strict TMP.)

Fair enough.

-- 
Dave Abrahams
Boost Consulting
http://www.boost-consulting.com

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