Boost logo

Boost Users :

Subject: Re: [Boost-users] [Proto] proto::function and constness
From: Eric Niebler (eric_at_[hidden])
Date: 2009-10-12 11:01:59


Kim Kuen Tang wrote:
> Hi all,
>
> let _o_ be any proto terminal and v a vector. I would like to extract
> the vector v from the expression _o_(v) to do some modification on this
> vector. For this purpose i defined a grammar Rhs to extract the most
> right hand side of the tree.
> But unfortunately the compiler is asking me for constness for this code:
>
> boost::result_of<Rhs(Expr)>::type & result = Rhs()(expr);
>
> Whereas the expression _o_ + v compiles fine without asking me for
> constness.
>
> Am I missing something?

You're not missing anything. Proto handle operator() differently than
the other operators: operator() captures its arguments by const ref,
whereas the other operators have overloads for const and non-const ref.
Why the difference? Because operator() can have up to
BOOST_PROTO_MAX_FUNCTION_CALL_ARITY arguments, which defaults to 5. To
accomodate every permutation of const and non-const arguments would
require 2^5 + 2^4 + 2^3 + 2^2 + 2^1 + 2^0 overloads, which is ... a lot.

So what are your options. my suggestion is to first change this:

     boost::result_of<Rhs(Expr)>::type & result = Rhs()(expr);

to more correct:

     boost::result_of<Rhs(Expr&)>::type result = Rhs()(expr);

Now, if you are certain that the result is really a mutable lvalue, you
can const_cast the result to a std::vector<int>& and mutate it.

The alternative would be to make _o_ an expression extension with
overloads of operator() to handle all the permutations.

-- 
Eric Niebler
BoostPro Computing
http://www.boostpro.com

Boost-users list run by williamkempf at hotmail.com, kalb at libertysoft.com, bjorn.karlsson at readsoft.com, gregod at cs.rpi.edu, wekempf at cox.net