140 lines
4.3 KiB
Plaintext
140 lines
4.3 KiB
Plaintext
[section:concepts Concepts]
|
|
|
|
[heading Expression]
|
|
|
|
_Expr_ is the central concept in _yap_. It must contain at least an _kind_
|
|
and a _tuple_ of values.
|
|
|
|
Here is a summary of the requirements on _Expr_. In the tables below, `E` is
|
|
a type that models _Expr_; `e` is an object of type `E`; `Tuple` is an
|
|
instantiation of _tuple_; and `t` is an object of type `Tuple`.
|
|
|
|
[table Expression Requirements
|
|
[[Expression] [Type] [Description] [Notes]]
|
|
[[`E::kind`] [_kind_] [ The kind of expression `E` is. ] [ Must be a compile-time constant. ]]
|
|
[[`e.elements`] [`Tuple`] [ The child expressions of `e`. ] [ The types of the elements must be appropriate to the kind of the expression. ]]
|
|
[[`E e{t}`] [] [ Construction/initialization of `e`. ] [ `t` must be stored in `e.elements`. ]]
|
|
]
|
|
|
|
As stated above, the `elements` data member must match the kind of the expression:
|
|
|
|
[table Expression Requirements
|
|
[[`E::kind`] [`hana::size(e.elements)`] [Possible Tuple Element Types] [Notes]]
|
|
|
|
[[`expr_kind::expr_ref`] [1] [ Any non-_expr_ref_ _Expr_. ] []]
|
|
[[`expr_kind::terminal`] [1] [ Any non-_Expr_. ] [A terminal with a _placeholder_ value will be treated as a placeholder. ]]
|
|
[[Any unary operator] [1] [ Any _Expr_. ] []]
|
|
[[Any binary operator] [2] [ Any _Expr_. ] []]
|
|
[[`expr_kind::if_else`] [3] [ Any _Expr_. ] []]
|
|
[[`expr_kind::call`] [Any number >= 1.] [ Any _Expr_. ] []]
|
|
]
|
|
|
|
[heading ExpressionTemplate]
|
|
|
|
_ExprTmpl_ is any template with two parameters that, when instantiated with an
|
|
_kind_ and a _tuple_, results in an _Expr_.
|
|
|
|
[heading Transform]
|
|
|
|
_xform_ takes a _XForm_ as its second parameter. A _XForm_ is a _Callable_
|
|
that takes expressions and returns values of unconstrained type. There are
|
|
two sorts of overloads _XForm_ may use: _ExprXForm_ and _TagXForm_.
|
|
|
|
A _XForm_ may have any number of overloads, including none.
|
|
|
|
[heading ExpressionTransform]
|
|
|
|
_ExprXForm_ takes an _Expr_ as its only parameter. Here are some examples.
|
|
|
|
This one takes any _Expr_:
|
|
|
|
struct xform
|
|
{
|
|
template <typename Expr>
|
|
auto operator() (Expr const & expr)
|
|
{
|
|
// ...
|
|
}
|
|
};
|
|
|
|
This one takes any type of _Expr_ that satisfies the constraints imposed by
|
|
its template parameters:
|
|
|
|
template <typename Expr1, typename Expr2, typename Expr3>
|
|
decltype(auto) xform (
|
|
boost::yap::expression<
|
|
boost::yap::expr_kind::plus,
|
|
boost::hana::tuple<
|
|
boost::yap::expression<
|
|
boost::yap::expr_kind::multiplies,
|
|
boost::hana::tuple<
|
|
Expr1,
|
|
Expr2
|
|
>
|
|
>,
|
|
Expr3
|
|
>
|
|
> const & expr
|
|
) {
|
|
// ...
|
|
}
|
|
|
|
This one takes only a specific type:
|
|
|
|
decltype(auto) xform (
|
|
decltype(term<number>{{0.0}} * number{} + number{}) const & expr
|
|
) {
|
|
// ...
|
|
}
|
|
|
|
[heading TagTransform]
|
|
|
|
_TagXForm_ takes a tag-type as its first parameter, and the individual
|
|
elements of an expression as the remaining parameters.
|
|
|
|
Tags are named such that the tag for an expression with _kind_
|
|
`expr_kind::foo` is named `foo_tag`. Here are some examples.
|
|
|
|
This one takes any terminal that contains a `user::number` (or reference to
|
|
such a terminal):
|
|
|
|
struct xform
|
|
{
|
|
decltype(auto) operator() (boost::yap::terminal_tag, user::number const & n)
|
|
{
|
|
// ...
|
|
}
|
|
};
|
|
|
|
This one takes any plus expression that contains a pair of `user::number`
|
|
terminals (or references to terminals):
|
|
|
|
decltype(auto) xform (boost::yap::plus_tag, user::number lhs, user::number rhs)
|
|
{
|
|
// ...
|
|
}
|
|
|
|
This one takes any negation expression:
|
|
|
|
struct xform
|
|
{
|
|
template <typename Expr>
|
|
decltype(auto) operator() (boost::yap::negate_tag, Expr const & expr)
|
|
{
|
|
// ...
|
|
}
|
|
};
|
|
|
|
This one takes any call expression with two terminals (or references to
|
|
terminals) containing values convertible to `double`:
|
|
|
|
struct xform
|
|
{
|
|
decltype(auto) operator() (boost::yap::call_tag, tag_type, double a, double b)
|
|
{
|
|
// ...
|
|
}
|
|
}
|
|
|
|
[endsect]
|