Boost logo

Boost :

Subject: Re: [boost] Help with Boost Preprocessor
From: Emil Dotchevski (emildotchevski_at_[hidden])
Date: 2009-08-30 04:56:51


Steven, thanks for your reply.

It is too late for me right now to understand your solution, but at
first look it seems like it's very close to what I need but not quite.
:)

The interface I need is something like:

CALL_PROD3(boost::bind(func(),_1,_2,_3,42),TYPE_LIST)

I do want to use bind (so I can pass any number of additional
arguments to the function), and I don't want the function name or the
type list macro name to be hard-coded. I just don't like the *nested*
use of bind in the solution I posted, and the fact that the type list
macro name is hard-coded in the helper functions fwd1 and fwd2.

Emil Dotchevski
Reverge Studios, Inc.
http://www.revergestudios.com/reblog/index.php?n=ReCode

On Sat, Aug 29, 2009 at 6:34 PM, Steven Watanabe<watanabesj_at_[hidden]> wrote:
> AMDG
>
> Emil Dotchevski wrote:
>>
>> Let's say I have a class template functor like this:
>>
>> struct
>> func
>>    {
>>    typedef void result_type;
>>
>>    template <class A1,class A2,class A3>
>>    void
>>    operator()( A1, A2, A3, int x )
>>        {
>>        }
>>    };
>>
>> Given a list of types, I want the function instantiated and called for
>> all permutations of the types in the list; the additional argument(s),
>> x, just need to be forwarded the same for all instances.
>>
>> Actually I got it working, see http://codepad.org/tnYTy9Iw.
>>
>> I don't think that my solution is very good though. First, it has some
>> run-time overhead due to the use of boost::bind in fwd1 and fwd2 (see
>> link above.) Second, I'd like the macro that defines the type list not
>> to be hard-coded in fwd1 and fwd2.
>>
>> Is this possible?
>>
>
> How does this work
>
> #include <boost/preprocessor/seq/for_each_product.hpp>
> #include <boost/preprocessor/seq/transform.hpp>
> #include <boost/preprocessor/seq/enum.hpp>
> #include <iostream>
>
> struct
> func
>   {
>   typedef void result_type;
>
>   template <class A1,class A2,class A3>
>   void
>   operator()( A1, A2, A3, int x )
>       {        std::cout <<
>           typeid(A1).name() << ',' <<
>           typeid(A2).name() << ',' <<
>           typeid(A3).name() << ',' <<
>           x << '\n';
>
>       }
>   };
>
> template<class T>
> T make() { return T(); }
>
> #define CALL_FUNC(r, args) func()(BOOST_PP_SEQ_ENUM(args), x);
> #define MAKE_OBJECT(s, data, elem) make<elem>()
> #define FUNC_II(types) \
>   BOOST_PP_SEQ_FOR_EACH_PRODUCT(CALL_FUNC, (types)(types)(types))
> #define FUNC_I(types) FUNC_II(types)
> #define FUNC(types, arg)                                        \
>   if(true) {                                                  \
>       int x = arg;                                            \
>       FUNC_I(BOOST_PP_SEQ_TRANSFORM(MAKE_OBJECT, ~, types))   \
>   } else ((void)0)
>
> int main() {
>   FUNC((int)(long), 42);
> }
>
> In Christ,
> Steven Watanabe
>
>
> _______________________________________________
> Unsubscribe & other changes:
> http://lists.boost.org/mailman/listinfo.cgi/boost


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