
On 1/15/2011 6:31 PM, Hossein Haeri wrote:
Dear all,
I have a syntax like
((_1 >> &f1 >> &f2) || (_2 >> &f3) || (_3 >> &f4 >> &f5 >> &f6)) >> g
for which I already have a small grammar which along with my context do their job fine. The above expression is to act like
g(f2(f1(x)), f3(y), f6(f5(f4(z))))
once invoked with _1 == x, _2 == y, and _3 == z. I am currently trying to add a safety layer on top of that which can emit a compile-error -- at the appropriate corner of my code -- that can prevent pass of functions with wrong arities. For example, g above needs to be a ternary.
Although my context will notice it if g is not a ternary and produce a meaningful error message, that's too late. My poor user needs to be informed right at the instantiation time. So, I thought I'm going to use transforms to get my grammar manage that.
<snip> Below is a grammar Stream that only matches these function stream expressions where the number of arguments to each callable matches the arity of the callable. It's a short hop from here to where you want to be, using is_callable_with_args. struct FunctionPtr : proto::and_< proto::terminal<_> , proto::if_<is_function<remove_pointer<proto::_value> >()> > {}; struct Stream; // The grammar for the thing that can appear on the // LHS of a >> operator, and a transform that computes // the arity of that expression. struct StreamArgs : proto::or_< proto::when< proto::terminal<_arg<_> > , mpl::int_<1>() > , proto::when< proto::logical_or<StreamArgs, StreamArgs> , mpl::plus< StreamArgs(proto::_left) , StreamArgs(proto::_right) >() > , proto::when< Stream , mpl::int_<1>() > > {}; struct Stream : proto::and_< proto::shift_right<StreamArgs, FunctionPtr> , proto::if_< mpl::equal_to< StreamArgs(proto::_left) , function_types::function_arity< proto::_value(proto::_right) >() >() > > {}; HTH, -- Eric Niebler BoostPro Computing http://www.boostpro.com