$include_dir="/home/hyper-archives/boost-users/include"; include("$include_dir/msg-header.inc") ?>
Subject: Re: [Boost-users] proto: analytical-only math functions
From: Eric Niebler (eric_at_[hidden])
Date: 2009-02-09 12:25:26
Hicham Mouline wrote:
> 
> Re my constants definitions (my constant terminals are defined as
> proto::terminal< constant_tag<24> >::type c24; ), the
> allowed syntax is :
>    c24 = const_expression;    // const_expression cannot include c24
> 
> a loose EBNF for my const_expression is:
> 
> const_expression :: integer-literal  e.g. 7
>                  |  floating-literal e.g. 5.4
>                  |  integer-type runtime variable e.g. int x, long y  (known
> only at runtime)
>                  |  fp runtime variable e.g. float r, double q (known only
> at runtime)
>                  |  my DSEL constants
>                  |  - const_expression
>                  |  const_expression + const_expression
>                  |  const_expression - const_expression
>                  |  const_expression * const_expression
>                  |  const_expression / const_expression
>                  |  const_expression % const_expression
>                  |  basic_function( const_expression )
>                  |  function( const_expression, ..., const_expression ) //
> respect the dimensionality
> 
> I don't see I am missing anything obvious?
I don't know, that's really for you to say as the DSEL designer.
> The concept of const_expression here is not meant that the value of the
> expression is known at compile-time.
> It only means that on taking the derivatives of my functions wrt to my DSEL
> variables, the const_expression disappears.
> 
> In order to exclude the constant being defined from the = RHS, I need to
> define the grammar wholly for LHS and RHS of =
> at the same time, I couldn't define RHS grammar alone because I need to
> exclude c24, right?
Not necessarily. I would just define the RHS grammar without worrying 
about excluding any particular constants. Then give your constants an 
overloaded operator= that uses a compile-time assertion to make sure the 
RHS doesn't contain the constant currently being assigned. Something 
like (untested) ...
template<class ID>
struct constant
   : proto::extends<
         typename proto::terminal<constant_impl<ID> >::type
       , constant<ID>
     >
{
     // For this constant, this grammar defines the valid
     // right-hand side expressions.
     struct RHS
       : proto::or_<
             proto::and_<
                 proto::terminal<_>
               , proto::not_<proto::terminal<constant_impl<ID> > >
             >
           , proto::nary_expr<_, proto::vararg<RHS> >
         >
     {};
     template<typename E>
     /* ... whatever you want this to return ... */
     operator=(E const &e) const
     {
         // Make sure E doesn't contain the constant
         // currently being assigned.
         BOOST_MPL_ASSERT((proto::matches<E, RHS>));
         /* ... whatever else you want here ... */
     }
};
HTH,
-- Eric Niebler BoostPro Computing http://www.boostpro.com