|
Boost : |
From: David Abrahams (dave_at_[hidden])
Date: 2003-03-23 07:56:03
"Jaap Suter" <J.Suter_at_[hidden]> writes:
>> It could be an instantiation depth issue. Maybe the OP's code needs
>> more of our loop unrolling technique to avoid deep instantiations. I
>> think that can be controlled by #defining BOOST_MPL_UNROLLING_LIMIT
>> to some number greater than 4 before mpl files are #included.
>
> Thanks, I already managed to fix it.
>
> It turned out to be a classic case of Effective MPL- item 5.13 with some
> added recursion issues.
>
> It was just weird, because before the 1.30.0 release everything was working
> fine, so it was some combination of my old code with new mpl code that
> triggered this error.
> Luckily, after a nice and long debug session, I managed to track the problem
> down to an inner-most loop, and then I simply had to rewrite it to make it
> work.
>
> Thanks for your help,
Jaap, I was just looking over the EMPL Wiki page (which continues to
be a great thing), and noticed that item 5.2 is not really a good
example of MPL style. In fact, you apply equal_to to an integral
constant and access its ::value_type member so I think it won't even
compile. Make that thing a true MPL metafunction (i.e. operate on
types only) and you get something much simpler:
template < class N, class Result = int_<0> >
struct num_bits_set
: apply_if<
equal_to<
N
, integral_c< typename N::value_type, 0 >
>
, Result
, num_bits_set<
integral_c< size_t, bitand_<N, arg<prev<N> > >
, next<Result>
>
>
{};
That "arg" template is something that Aleksey and I have discussed
which causes a nullary metafunction to be evaluated in a lambda
expression. It may have another name in the current MPL sources; I'm
not absolutely sure (Aleksey?)
I also think it would be a great idea to have "zero" and "one"
metafunctions (which also satisfy the integral constant wrapper
requirements) so that we could write the above as:
template < class N, class Result = int_<0> >
struct num_bits_set
: apply_if<
equal_to<N, zero<N> >
, Result
, num_bits_set<
integral_c< size_t, bitand_<N, arg<prev<N> > >
, next<Result>
>
>
{};
If we wanted to get funky we could make it so zero<int_<3> > and
zero<long> both work.
-- Dave Abrahams Boost Consulting 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