|
Boost-Commit : |
Subject: [Boost-commit] svn:boost r62736 - in trunk: boost/proto boost/proto/detail libs/proto/doc/reference
From: eric_at_[hidden]
Date: 2010-06-10 10:07:02
Author: eric_niebler
Date: 2010-06-10 10:07:00 EDT (Thu, 10 Jun 2010)
New Revision: 62736
URL: http://svn.boost.org/trac/boost/changeset/62736
Log:
capture behavior can specified on a per-domain basis. Finally
Added:
trunk/boost/proto/detail/as_expr.hpp (contents, props changed)
Text files modified:
trunk/boost/proto/args.hpp | 16 ++
trunk/boost/proto/deep_copy.hpp | 27 +--
trunk/boost/proto/domain.hpp | 89 ++++++++---
trunk/boost/proto/expr.hpp | 11 -
trunk/boost/proto/generate.hpp | 37 +++++
trunk/boost/proto/literal.hpp | 4
trunk/boost/proto/make_expr.hpp | 42 ++--
trunk/boost/proto/proto_fwd.hpp | 30 +--
trunk/boost/proto/traits.hpp | 295 ++++++---------------------------------
trunk/libs/proto/doc/reference/literal.xml | 4
10 files changed, 199 insertions(+), 356 deletions(-)
Modified: trunk/boost/proto/args.hpp
==============================================================================
--- trunk/boost/proto/args.hpp (original)
+++ trunk/boost/proto/args.hpp 2010-06-10 10:07:00 EDT (Thu, 10 Jun 2010)
@@ -11,6 +11,7 @@
#ifndef BOOST_PROTO_ARGS_HPP_EAN_04_01_2005
#define BOOST_PROTO_ARGS_HPP_EAN_04_01_2005
+ #include <iosfwd>
#include <boost/config.hpp>
#include <boost/detail/workaround.hpp>
#include <boost/preprocessor/cat.hpp>
@@ -20,7 +21,10 @@
#include <boost/preprocessor/repetition/repeat.hpp>
#include <boost/preprocessor/repetition/repeat_from_to.hpp>
#include <boost/type_traits/is_function.hpp>
+ #include <boost/type_traits/is_abstract.hpp>
+ #include <boost/type_traits/is_base_of.hpp>
#include <boost/mpl/if.hpp>
+ #include <boost/mpl/or.hpp>
#include <boost/mpl/void.hpp>
#include <boost/proto/proto_fwd.hpp>
@@ -29,6 +33,16 @@
namespace detail
{
/// INTERNAL ONLY
+ template<typename T>
+ struct ref_only
+ : mpl::or_<
+ is_function<T>
+ , is_abstract<T>
+ , is_base_of<std::ios_base, T>
+ >
+ {};
+
+ /// INTERNAL ONLY
template<typename Expr>
struct expr_traits
{
@@ -68,7 +82,7 @@
template<typename T>
struct term_traits<T &>
{
- typedef typename mpl::if_c<is_function<T>::value, T &, T>::type value_type;
+ typedef typename mpl::if_c<ref_only<T>::value, T &, T>::type value_type;
typedef T &reference;
typedef T &const_reference;
};
Modified: trunk/boost/proto/deep_copy.hpp
==============================================================================
--- trunk/boost/proto/deep_copy.hpp (original)
+++ trunk/boost/proto/deep_copy.hpp 2010-06-10 10:07:00 EDT (Thu, 10 Jun 2010)
@@ -14,9 +14,9 @@
#include <boost/preprocessor/repetition/enum.hpp>
#include <boost/preprocessor/iteration/iterate.hpp>
#include <boost/mpl/if.hpp>
- #include <boost/type_traits/is_function.hpp>
#include <boost/type_traits/remove_reference.hpp>
#include <boost/proto/proto_fwd.hpp>
+ #include <boost/proto/args.hpp>
#include <boost/proto/expr.hpp>
namespace boost { namespace proto
@@ -29,32 +29,21 @@
template<typename Expr>
struct deep_copy_impl<Expr, 0>
{
- typedef BOOST_PROTO_UNCVREF(typename Expr::proto_child0) raw_terminal_type;
-
- // can't store a function type in a terminal.
- typedef
- typename mpl::if_c<
- is_function<raw_terminal_type>::value
- , typename Expr::proto_child0
- , raw_terminal_type
- >::type
- actual_terminal_type;
-
typedef
typename base_expr<
typename Expr::proto_domain
, tag::terminal
- , term<actual_terminal_type>
+ , term<typename term_traits<typename Expr::proto_child0>::value_type>
>::type
- expr_;
+ expr_type;
typedef typename Expr::proto_generator proto_generator;
- typedef typename proto_generator::template result<proto_generator(expr_)>::type result_type;
+ typedef typename proto_generator::template result<proto_generator(expr_type)>::type result_type;
template<typename Expr2, typename S, typename D>
result_type operator()(Expr2 const &e, S const &, D const &) const
{
- return proto_generator()(expr_::make(e.proto_base().child0));
+ return proto_generator()(expr_type::make(e.proto_base().child0));
}
};
}
@@ -203,15 +192,15 @@
BOOST_PP_ENUM(N, BOOST_PROTO_DEFINE_DEEP_COPY_TYPE, ~)
>
>::type
- expr_;
+ expr_type;
typedef typename Expr::proto_generator proto_generator;
- typedef typename proto_generator::template result<proto_generator(expr_)>::type result_type;
+ typedef typename proto_generator::template result<proto_generator(expr_type)>::type result_type;
template<typename Expr2, typename S, typename D>
result_type operator()(Expr2 const &e, S const &, D const &) const
{
- expr_ const that = {
+ expr_type const that = {
BOOST_PP_ENUM(N, BOOST_PROTO_DEFINE_DEEP_COPY_FUN, ~)
};
Added: trunk/boost/proto/detail/as_expr.hpp
==============================================================================
--- (empty file)
+++ trunk/boost/proto/detail/as_expr.hpp 2010-06-10 10:07:00 EDT (Thu, 10 Jun 2010)
@@ -0,0 +1,271 @@
+///////////////////////////////////////////////////////////////////////////////
+/// \file as_expr.hpp
+/// Contains definition of the as_expr\<\> and as_child\<\> helper class
+/// templates used to implement proto::domain's as_expr\<\> and as_child\<\>
+/// member templates.
+//
+// Copyright 2010 Eric Niebler. Distributed under the Boost
+// Software License, Version 1.0. (See accompanying file
+// LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
+
+#ifndef BOOST_PROTO_DETAIL_AS_EXPR_HPP_EAN_06_09_2010
+#define BOOST_PROTO_DETAIL_AS_EXPR_HPP_EAN_06_09_2010
+
+#include <boost/type_traits/is_same.hpp>
+#include <boost/proto/proto_fwd.hpp>
+#include <boost/proto/args.hpp>
+
+namespace boost { namespace proto { namespace detail
+{
+ ////////////////////////////////////////////////////////////////////////////////////////////////
+ template<
+ typename T
+ , typename Generator
+ , bool IsExpr = is_expr<T>::value
+ , bool WantsBasicExpr = wants_basic_expr<Generator>::value
+ >
+ struct as_expr;
+
+ ////////////////////////////////////////////////////////////////////////////////////////////////
+ template<
+ typename T
+ , typename Generator
+ , bool IsExpr = is_expr<T>::value
+ , bool WantsBasicExpr = wants_basic_expr<Generator>::value
+ >
+ struct as_child;
+
+ ////////////////////////////////////////////////////////////////////////////////////////////////
+ template<typename Expr, typename Generator, bool SameGenerator>
+ struct already_expr
+ {
+ typedef typename Expr::proto_derived_expr uncv_expr_type;
+ typedef typename Generator::template result<Generator(uncv_expr_type)>::type result_type;
+
+ result_type operator()(Expr &e) const
+ {
+ return Generator()(e);
+ }
+ };
+
+ ////////////////////////////////////////////////////////////////////////////////////////////////
+ template<typename Expr, typename Generator>
+ struct already_expr<Expr, Generator, true>
+ {
+ typedef typename Expr::proto_derived_expr result_type;
+
+ result_type operator()(Expr &e) const
+ {
+ return e;
+ }
+ };
+
+ ////////////////////////////////////////////////////////////////////////////////////////////////
+ template<typename Expr, typename Generator, bool SameGenerator>
+ struct already_child
+ {
+ typedef typename Expr::proto_derived_expr uncv_expr_type;
+ typedef typename Generator::template result<Generator(uncv_expr_type)>::type result_type;
+
+ result_type operator()(Expr &e) const
+ {
+ return Generator()(e);
+ }
+ };
+
+ ////////////////////////////////////////////////////////////////////////////////////////////////
+ template<typename Expr, typename Generator>
+ struct already_child<Expr, Generator, true>
+ {
+ typedef Expr &result_type;
+
+ result_type operator()(Expr &e) const
+ {
+ return e;
+ }
+ };
+
+ ////////////////////////////////////////////////////////////////////////////////////////////////
+ template<typename T, typename Generator>
+ struct as_expr<T, Generator, false, false>
+ {
+ typedef typename term_traits<T &>::value_type value_type;
+ typedef proto::expr<proto::tag::terminal, term<value_type>, 0> expr_type;
+ typedef typename Generator::template result<Generator(expr_type)>::type result_type;
+
+ result_type operator()(T &t) const
+ {
+ return Generator()(expr_type::make(t));
+ }
+ };
+
+ ////////////////////////////////////////////////////////////////////////////////////////////////
+ template<typename T, typename Generator>
+ struct as_expr<T, Generator, false, true>
+ {
+ typedef typename term_traits<T &>::value_type value_type;
+ typedef proto::basic_expr<proto::tag::terminal, term<value_type>, 0> expr_type;
+ typedef typename Generator::template result<Generator(expr_type)>::type result_type;
+
+ result_type operator()(T &t) const
+ {
+ return Generator()(expr_type::make(t));
+ }
+ };
+
+ ////////////////////////////////////////////////////////////////////////////////////////////////
+ template<typename T, typename Generator>
+ struct as_expr<T, Generator, true, false>
+ : already_expr<
+ T
+ , Generator
+ , is_same<
+ typename Generator::proto_base_generator
+ , typename T::proto_generator::proto_base_generator
+ >::value
+ >
+ {};
+
+ ////////////////////////////////////////////////////////////////////////////////////////////////
+ template<typename T, typename Generator>
+ struct as_expr<T, Generator, true, true>
+ : already_expr<
+ T
+ , Generator
+ , is_same<
+ typename Generator::proto_base_generator
+ , typename T::proto_generator::proto_base_generator
+ >::value
+ >
+ {};
+
+ ////////////////////////////////////////////////////////////////////////////////////////////////
+ template<typename T>
+ struct as_expr<T, proto::_, false, false>
+ {
+ typedef typename term_traits<T &>::value_type value_type;
+ typedef proto::expr<proto::tag::terminal, term<value_type>, 0> result_type;
+
+ result_type operator()(T &t) const
+ {
+ return result_type::make(t);
+ }
+ };
+
+ ////////////////////////////////////////////////////////////////////////////////////////////////
+ template<typename T>
+ struct as_expr<T, proto::_, false, true>
+ {
+ typedef typename term_traits<T &>::value_type value_type;
+ typedef proto::basic_expr<proto::tag::terminal, term<value_type>, 0> result_type;
+
+ result_type operator()(T &t) const
+ {
+ return result_type::make(t);
+ }
+ };
+
+ ////////////////////////////////////////////////////////////////////////////////////////////////
+ template<typename T>
+ struct as_expr<T, proto::_, true, false>
+ : already_expr<T, proto::_, true>
+ {};
+
+ ////////////////////////////////////////////////////////////////////////////////////////////////
+ template<typename T>
+ struct as_expr<T, proto::_, true, true>
+ : already_expr<T, proto::_, true>
+ {};
+
+
+ ////////////////////////////////////////////////////////////////////////////////////////////////
+ template<typename T, typename Generator>
+ struct as_child<T, Generator, false, false>
+ {
+ typedef proto::expr<proto::tag::terminal, term<T &>, 0> expr_type;
+ typedef typename Generator::template result<Generator(expr_type)>::type result_type;
+
+ result_type operator()(T &t) const
+ {
+ return Generator()(expr_type::make(t));
+ }
+ };
+
+ ////////////////////////////////////////////////////////////////////////////////////////////////
+ template<typename T, typename Generator>
+ struct as_child<T, Generator, false, true>
+ {
+ typedef proto::basic_expr<proto::tag::terminal, term<T &>, 0> expr_type;
+ typedef typename Generator::template result<Generator(expr_type)>::type result_type;
+
+ result_type operator()(T &t) const
+ {
+ return Generator()(expr_type::make(t));
+ }
+ };
+
+ ////////////////////////////////////////////////////////////////////////////////////////////////
+ template<typename T, typename Generator>
+ struct as_child<T, Generator, true, false>
+ : already_child<
+ T
+ , Generator
+ , is_same<
+ typename Generator::proto_base_generator
+ , typename T::proto_generator::proto_base_generator
+ >::value
+ >
+ {};
+
+ ////////////////////////////////////////////////////////////////////////////////////////////////
+ template<typename T, typename Generator>
+ struct as_child<T, Generator, true, true>
+ : already_child<
+ T
+ , Generator
+ , is_same<
+ typename Generator::proto_base_generator
+ , typename T::proto_generator::proto_base_generator
+ >::value
+ >
+ {};
+
+ ////////////////////////////////////////////////////////////////////////////////////////////////
+ template<typename T>
+ struct as_child<T, proto::_, false, false>
+ {
+ typedef proto::expr<proto::tag::terminal, term<T &>, 0> result_type;
+
+ result_type operator()(T &t) const
+ {
+ return result_type::make(t);
+ }
+ };
+
+ ////////////////////////////////////////////////////////////////////////////////////////////////
+ template<typename T>
+ struct as_child<T, proto::_, false, true>
+ {
+ typedef proto::basic_expr<proto::tag::terminal, term<T &>, 0> result_type;
+
+ result_type operator()(T &t) const
+ {
+ return result_type::make(t);
+ }
+ };
+
+ ////////////////////////////////////////////////////////////////////////////////////////////////
+ template<typename T>
+ struct as_child<T, proto::_, true, false>
+ : already_child<T, proto::_, true>
+ {};
+
+ ////////////////////////////////////////////////////////////////////////////////////////////////
+ template<typename T>
+ struct as_child<T, proto::_, true, true>
+ : already_child<T, proto::_, true>
+ {};
+
+}}}
+
+#endif
Modified: trunk/boost/proto/domain.hpp
==============================================================================
--- trunk/boost/proto/domain.hpp (original)
+++ trunk/boost/proto/domain.hpp 2010-06-10 10:07:00 EDT (Thu, 10 Jun 2010)
@@ -13,6 +13,8 @@
#include <boost/ref.hpp>
#include <boost/proto/proto_fwd.hpp>
+#include <boost/proto/generate.hpp>
+#include <boost/proto/detail/as_expr.hpp>
#include <boost/proto/detail/deduce_domain.hpp>
namespace boost { namespace proto
@@ -89,9 +91,66 @@
typedef Generator proto_generator;
typedef Grammar proto_grammar;
typedef Super proto_super_domain;
+ typedef domain proto_base_domain;
/// INTERNAL ONLY
typedef void proto_is_domain_;
+
+ /// \brief A monomorphic unary function object that turns objects into Proto
+ /// expression objects in this domain.
+ ///
+ /// The <tt>as_expr\<\></tt> function object turns objects into Proto expressions, if
+ /// they are not already, by making them Proto terminals held by value if
+ /// possible. Objects that are already Proto expressions are left alone.
+ ///
+ /// If <tt>wants_basic_expr\<Generator\>::value</tt> is true, then let \c E be \c basic_expr;
+ /// otherwise, let \t E be \c expr. Given an lvalue \c t of type \c T:
+ ///
+ /// If \c T is not a Proto expression type the resulting terminal is
+ /// calculated as follows:
+ ///
+ /// If \c T is a function type, an abstract type, or a type derived from
+ /// \c std::ios_base, let \c A be <tt>T &</tt>.
+ /// Otherwise, let \c A be the type \c T stripped of cv-qualifiers.
+ /// Then, the result of applying <tt>as_expr\<T\>()(t)</tt> is
+ /// <tt>Generator()(E\<tag::terminal, term\<A\> \>::make(t))</tt>.
+ ///
+ /// If \c T is a Proto expression type and its generator type is different from
+ /// \c Generator, the result is <tt>Generator()(t)</tt>.
+ ///
+ /// Otherwise, the result is \c t converted to an (un-const) rvalue.
+ ///
+ template<typename T, typename Callable = proto::callable>
+ struct as_expr
+ : detail::as_expr<T, Generator>
+ {
+ BOOST_PROTO_CALLABLE()
+ };
+
+ /// \brief A monomorphic unary function object that turns objects into Proto
+ /// expression objects in this domain.
+ ///
+ /// The <tt>as_child\<\></tt> function object turns objects into Proto expressions, if
+ /// they are not already, by making them Proto terminals held by reference.
+ /// Objects that are already Proto expressions are simply returned by reference.
+ ///
+ /// If <tt>wants_basic_expr\<Generator\>::value</tt> is true, then let \c E be \c basic_expr;
+ /// otherwise, let \t E be \c expr. Given an lvalue \c t of type \c T:
+ ///
+ /// If \c T is not a Proto expression type the resulting terminal is
+ /// <tt>Generator()(E\<tag::terminal, term\<T &\> \>::make(t))</tt>.
+ ///
+ /// If \c T is a Proto expression type and its generator type is different from
+ /// \c Generator, the result is <tt>Generator()(t)</tt>.
+ ///
+ /// Otherwise, the result is the lvalue \c t.
+ ///
+ template<typename T, typename Callable = proto::callable>
+ struct as_child
+ : detail::as_child<T, Generator>
+ {
+ BOOST_PROTO_CALLABLE()
+ };
};
/// \brief The domain expressions have by default, if
@@ -173,26 +232,12 @@
typedef typename domain_of<T>::type type;
};
- /// \brief Tests a domain to see whether its generator would prefer
- /// to be passed instances of \c proto::basic_expr\<\> rather than
- /// \c proto::expr\<\>.
- ///
- template<typename Domain, typename Void>
- struct wants_basic_expr
- : mpl::false_
- {};
-
- template<typename Domain>
- struct wants_basic_expr<Domain, typename Domain::proto_use_basic_expr_>
- : mpl::true_
- {};
-
/// \brief Given a domain, a tag type and an argument list,
/// compute the type of the expression to generate. This is
/// either an instance of \c proto::expr\<\> or
/// \c proto::basic_expr\<\>.
///
- template<typename Domain, typename Tag, typename Args, typename Void>
+ template<typename Domain, typename Tag, typename Args, typename Void /*= void*/>
struct base_expr
{
typedef proto::expr<Tag, Args, Args::arity> type;
@@ -201,23 +246,11 @@
/// INTERNAL ONLY
///
template<typename Domain, typename Tag, typename Args>
- struct base_expr<Domain, Tag, Args, typename Domain::proto_use_basic_expr_>
+ struct base_expr<Domain, Tag, Args, typename Domain::proto_generator::proto_use_basic_expr_>
{
typedef proto::basic_expr<Tag, Args, Args::arity> type;
};
- /// \brief Annotate a domain to indicate that its generator would
- /// prefer to be passed instances of \c proto::basic_expr\<\> rather
- /// than \c proto::expr\<\>. <tt>use_basic_expr\<Domain\></tt> is
- /// itself a domain.
- ///
- template<typename Domain>
- struct use_basic_expr
- : Domain
- {
- BOOST_PROTO_USE_BASIC_EXPR()
- };
-
}}
#endif
Modified: trunk/boost/proto/expr.hpp
==============================================================================
--- trunk/boost/proto/expr.hpp (original)
+++ trunk/boost/proto/expr.hpp 2010-06-10 10:07:00 EDT (Thu, 10 Jun 2010)
@@ -122,17 +122,6 @@
#include BOOST_PP_ITERATE()
}
- // TODO consider adding a basic_expr<> that doesn't have operator=,
- // operator[] or operator() for use by BOOST_PROTO_BASIC_EXTENDS().
- // Those member functions are unused in that case, and only slow
- // down instantiations. basic_expr::proto_base_expr can still be
- // expr<> because uses of proto_base_expr in proto::matches<> shouldn't
- // cause the expr<> type to be instantiated. (<-- Check that assumtion!)
- // OR, should expr<>::proto_base_expr be a typedef for basic_expr<>?
- // It should, and proto_base() can return *this reinterpret_cast to
- // a basic_expr because they should be layout compatible. Or not, because
- // that would incur an extra template instantiation. :-(
-
namespace exprns_
{
// The expr<> specializations are actually defined here.
Modified: trunk/boost/proto/generate.hpp
==============================================================================
--- trunk/boost/proto/generate.hpp (original)
+++ trunk/boost/proto/generate.hpp 2010-06-10 10:07:00 EDT (Thu, 10 Jun 2010)
@@ -18,6 +18,7 @@
#include <boost/preprocessor/repetition/enum_params.hpp>
#include <boost/preprocessor/repetition/enum_binary_params.hpp>
#include <boost/preprocessor/repetition/enum_trailing_params.hpp>
+ #include <boost/mpl/bool.hpp>
#include <boost/utility/enable_if.hpp>
#include <boost/utility/result_of.hpp>
#include <boost/proto/proto_fwd.hpp>
@@ -87,6 +88,8 @@
{
BOOST_PROTO_CALLABLE()
+ typedef default_generator proto_base_generator;
+
template<typename Sig>
struct result;
@@ -124,6 +127,8 @@
BOOST_PROTO_CALLABLE()
BOOST_PROTO_USE_BASIC_EXPR()
+ typedef generator proto_base_generator;
+
template<typename Sig>
struct result;
@@ -170,6 +175,8 @@
BOOST_PROTO_CALLABLE()
BOOST_PROTO_USE_BASIC_EXPR()
+ typedef pod_generator proto_base_generator;
+
template<typename Sig>
struct result;
@@ -217,6 +224,8 @@
{
BOOST_PROTO_CALLABLE()
+ typedef by_value_generator proto_base_generator;
+
template<typename Sig>
struct result;
@@ -268,6 +277,8 @@
{
BOOST_PROTO_CALLABLE()
+ typedef compose_generators proto_base_generator;
+
template<typename Sig>
struct result;
@@ -310,6 +321,32 @@
}
};
+ /// \brief Annotate a generator to indicate that it would
+ /// prefer to be passed instances of \c proto::basic_expr\<\> rather
+ /// than \c proto::expr\<\>. <tt>use_basic_expr\<Generator\></tt> is
+ /// itself a generator.
+ ///
+ template<typename Generator>
+ struct use_basic_expr
+ : Generator
+ {
+ BOOST_PROTO_USE_BASIC_EXPR()
+ };
+
+ /// \brief Tests a generator to see whether it would prefer
+ /// to be passed instances of \c proto::basic_expr\<\> rather than
+ /// \c proto::expr\<\>.
+ ///
+ template<typename Generator, typename Void>
+ struct wants_basic_expr
+ : mpl::false_
+ {};
+
+ template<typename Generator>
+ struct wants_basic_expr<Generator, typename Generator::proto_use_basic_expr_>
+ : mpl::true_
+ {};
+
/// INTERNAL ONLY
template<>
struct is_callable<default_generator>
Modified: trunk/boost/proto/literal.hpp
==============================================================================
--- trunk/boost/proto/literal.hpp (original)
+++ trunk/boost/proto/literal.hpp 2010-06-10 10:07:00 EDT (Thu, 10 Jun 2010)
@@ -34,10 +34,10 @@
, typename Domain // = default_domain
>
struct literal
- : extends<expr<tag::terminal, term<T>, 0>, literal<T, Domain>, Domain>
+ : extends<basic_expr<tag::terminal, term<T>, 0>, literal<T, Domain>, Domain>
{
private:
- typedef expr<tag::terminal, term<T>, 0> terminal_type;
+ typedef basic_expr<tag::terminal, term<T>, 0> terminal_type;
typedef extends<terminal_type, literal<T, Domain>, Domain> base_type;
public:
Modified: trunk/boost/proto/make_expr.hpp
==============================================================================
--- trunk/boost/proto/make_expr.hpp (original)
+++ trunk/boost/proto/make_expr.hpp 2010-06-10 10:07:00 EDT (Thu, 10 Jun 2010)
@@ -71,19 +71,19 @@
/// INTERNAL ONLY
///
#define BOOST_PROTO_AS_CHILD_TYPE(Z, N, DATA) \
- typename boost::proto::detail::protoify_< \
+ typename boost::proto::detail::protoify< \
BOOST_PP_CAT(BOOST_PP_TUPLE_ELEM(3, 0, DATA), N) \
, BOOST_PP_TUPLE_ELEM(3, 2, DATA) \
- >::type \
+ >::result_type \
/**/
/// INTERNAL ONLY
///
#define BOOST_PROTO_AS_CHILD(Z, N, DATA) \
- boost::proto::detail::protoify_< \
+ boost::proto::detail::protoify< \
BOOST_PP_CAT(BOOST_PP_TUPLE_ELEM(3, 0, DATA), N) \
, BOOST_PP_TUPLE_ELEM(3, 2, DATA) \
- >::call(BOOST_PP_CAT(BOOST_PP_TUPLE_ELEM(3, 1, DATA), N)) \
+ >()(BOOST_PP_CAT(BOOST_PP_TUPLE_ELEM(3, 1, DATA), N)) \
/**/
/// INTERNAL ONLY
@@ -136,41 +136,41 @@
/// INTERNAL ONLY
///
#define BOOST_PROTO_FUSION_AS_CHILD_AT_TYPE(Z, N, DATA) \
- typename detail::protoify_< \
+ typename detail::protoify< \
BOOST_PROTO_FUSION_AT_TYPE(Z, N, DATA) \
, Domain \
- >::type \
+ >::result_type \
/**/
/// INTERNAL ONLY
///
#define BOOST_PROTO_FUSION_AS_CHILD_AT(Z, N, DATA) \
- detail::protoify_< \
+ detail::protoify< \
BOOST_PROTO_FUSION_AT_TYPE(Z, N, DATA) \
, Domain \
- >::call(BOOST_PROTO_FUSION_AT(Z, N, DATA)) \
+ >()(BOOST_PROTO_FUSION_AT(Z, N, DATA)) \
/**/
namespace detail
{
template<typename T, typename Domain>
- struct protoify_
- : result_of::as_expr<T, Domain>
+ struct protoify
+ : Domain::template as_expr<T>
{};
template<typename T, typename Domain>
- struct protoify_<T &, Domain>
- : result_of::as_child<T, Domain>
+ struct protoify<T &, Domain>
+ : Domain::template as_child<T>
{};
template<typename T, typename Domain>
- struct protoify_<boost::reference_wrapper<T>, Domain>
- : result_of::as_child<T, Domain>
+ struct protoify<boost::reference_wrapper<T>, Domain>
+ : Domain::template as_child<T>
{};
template<typename T, typename Domain>
- struct protoify_<boost::reference_wrapper<T> const, Domain>
- : result_of::as_child<T, Domain>
+ struct protoify<boost::reference_wrapper<T> const, Domain>
+ : Domain::template as_child<T>
{};
template<typename Tag, typename Domain, typename Sequence, std::size_t Size>
@@ -189,15 +189,15 @@
terminal_type;
typedef
- typename proto::detail::protoify_<
+ typename proto::detail::protoify<
terminal_type
, Domain
- >::type
+ >::result_type
type;
static type const call(Sequence const &sequence)
{
- return proto::detail::protoify_<terminal_type, Domain>::call(fusion::at_c<0>(sequence));
+ return proto::detail::protoify<terminal_type, Domain>()(fusion::at_c<0>(sequence));
}
};
@@ -223,11 +223,11 @@
struct make_expr_<tag::terminal, Domain, A
BOOST_PP_ENUM_TRAILING_PARAMS(BOOST_PROTO_MAX_ARITY, void BOOST_PP_INTERCEPT)>
{
- typedef typename proto::detail::protoify_<A, Domain>::type result_type;
+ typedef typename proto::detail::protoify<A, Domain>::result_type result_type;
result_type operator()(typename add_reference<A>::type a) const
{
- return proto::detail::protoify_<A, Domain>::call(a);
+ return proto::detail::protoify<A, Domain>()(a);
}
};
Modified: trunk/boost/proto/proto_fwd.hpp
==============================================================================
--- trunk/boost/proto/proto_fwd.hpp (original)
+++ trunk/boost/proto/proto_fwd.hpp 2010-06-10 10:07:00 EDT (Thu, 10 Jun 2010)
@@ -251,6 +251,12 @@
template<typename First, typename Second>
struct compose_generators;
+ template<typename Generator, typename Void = void>
+ struct wants_basic_expr;
+
+ template<typename Generator>
+ struct use_basic_expr;
+
////////////////////////////////////////////////////////////////////////////////////////////////
template<
typename Generator = default_generator
@@ -263,15 +269,9 @@
struct deduce_domain;
- template<typename Domain, typename Void = void>
- struct wants_basic_expr;
-
template<typename Domain, typename Tag, typename Args, typename Void = void>
struct base_expr;
- template<typename Domain>
- struct use_basic_expr;
-
////////////////////////////////////////////////////////////////////////////////////////////////
namespace exprns_
{
@@ -363,24 +363,10 @@
namespace result_of
{
- template<
- typename T
- , typename Domain = default_domain
- , typename Void = void
- #ifdef BOOST_PROTO_BROKEN_PTS
- , typename Void2 = void
- #endif
- >
+ template<typename T, typename Domain = default_domain>
struct as_expr;
- template<
- typename T
- , typename Domain = default_domain
- , typename Void = void
- #ifdef BOOST_PROTO_BROKEN_PTS
- , typename Void2 = void
- #endif
- >
+ template<typename T, typename Domain = default_domain>
struct as_child;
template<typename Expr, typename N = mpl::long_<0> >
Modified: trunk/boost/proto/traits.hpp
==============================================================================
--- trunk/boost/proto/traits.hpp (original)
+++ trunk/boost/proto/traits.hpp 2010-06-10 10:07:00 EDT (Thu, 10 Jun 2010)
@@ -17,31 +17,19 @@
#include <boost/preprocessor/iteration/iterate.hpp>
#include <boost/preprocessor/repetition/enum.hpp>
#include <boost/preprocessor/repetition/enum_params.hpp>
- #include <boost/preprocessor/repetition/enum_trailing.hpp>
#include <boost/preprocessor/repetition/enum_trailing_params.hpp>
#include <boost/preprocessor/repetition/repeat.hpp>
#include <boost/preprocessor/repetition/repeat_from_to.hpp>
#include <boost/preprocessor/facilities/intercept.hpp>
#include <boost/preprocessor/arithmetic/sub.hpp>
- #include <boost/ref.hpp>
- #include <boost/mpl/if.hpp>
- #include <boost/mpl/or.hpp>
#include <boost/mpl/bool.hpp>
- #include <boost/mpl/eval_if.hpp>
#include <boost/mpl/aux_/template_arity.hpp>
#include <boost/mpl/aux_/lambda_arity_param.hpp>
- #include <boost/static_assert.hpp>
- #include <boost/utility/result_of.hpp>
- #include <boost/utility/enable_if.hpp>
#include <boost/type_traits/is_pod.hpp>
#include <boost/type_traits/is_same.hpp>
- #include <boost/type_traits/is_function.hpp>
- #include <boost/type_traits/remove_cv.hpp>
- #include <boost/type_traits/add_reference.hpp>
#include <boost/proto/proto_fwd.hpp>
#include <boost/proto/args.hpp>
- #include <boost/proto/tags.hpp>
- #include <boost/proto/generate.hpp>
+ #include <boost/proto/domain.hpp>
#include <boost/proto/transform/pass_through.hpp>
#if BOOST_WORKAROUND( BOOST_MSVC, >= 1400 )
@@ -237,211 +225,18 @@
{
/// \brief A metafunction that computes the return type of the \c as_expr()
/// function.
- ///
- /// The <tt>as_expr\<\></tt> metafunction turns types into Proto types, if
- /// they are not already, by making them Proto terminals held by value if
- /// possible. Types which are already Proto types are left alone.
- ///
- /// This specialization is selected when the type is not yet a Proto type.
- /// The resulting terminal type is calculated as follows:
- ///
- /// If \c T is a function type, let \c A be <tt>T &</tt>.
- /// Otherwise, let \c A be the type \c T stripped of cv-qualifiers.
- /// Then, the result type <tt>as_expr\<T, Domain\>::type</tt> is
- /// <tt>boost::result_of\<Domain(expr\< tag::terminal, term\<A\> \>)\>::type</tt>.
- template<
- typename T
- , typename Domain // = default_domain
- , typename Void // = void
- #ifdef BOOST_PROTO_BROKEN_PTS
- , typename Void2 // = void
- #endif
- >
+ template<typename T, typename Domain /*= default_domain*/>
struct as_expr
{
- typedef
- typename mpl::eval_if_c<
- is_function<T>::value
- , add_reference<T>
- , remove_cv<T>
- >::type
- arg0_;
- typedef typename base_expr<Domain, proto::tag::terminal, term<arg0_> >::type expr_;
- typedef typename Domain::proto_generator proto_generator;
- typedef typename proto_generator::template result<Domain(expr_)>::type type;
- typedef type const reference;
-
- /// INTERNAL ONLY
- ///
- template<typename T2>
- static reference call(T2 &t)
- {
- return proto_generator()(expr_::make(static_cast<T &>(t)));
- }
- };
-
- /// \brief A metafunction that computes the return type of the \c as_expr()
- /// function.
- ///
- /// The <tt>as_expr\<\></tt> metafunction turns types into Proto types, if
- /// they are not already, by making them Proto terminals held by value if
- /// possible. Types which are already Proto types are left alone.
- ///
- /// This specialization is selected when the type is already a Proto type.
- /// The result type <tt>as_expr\<T, Domain\>::type</tt> is \c T stripped
- /// of cv-qualifiers.
- template<typename T, typename Domain>
- struct as_expr<
- T
- , Domain
- , typename T::proto_is_expr_
- #ifdef BOOST_PROTO_BROKEN_PTS
- , typename disable_if<is_same<Domain, typename T::proto_domain> >::type
- #endif
- >
- {
- typedef typename T::proto_derived_expr expr_; // removes the const
- typedef typename Domain::proto_generator proto_generator;
- typedef typename proto_generator::template result<proto_generator(expr_)>::type type;
- typedef type const reference;
-
- /// INTERNAL ONLY
- ///
- template<typename T2>
- static reference call(T2 &t)
- {
- return proto_generator()(static_cast<T &>(t));
- }
- };
-
- template<typename T>
- struct as_expr<
- T
- , typename T::proto_domain
- , typename T::proto_is_expr_
- #ifdef BOOST_PROTO_BROKEN_PTS
- , void
- #endif
- >
- {
- typedef typename T::proto_derived_expr type; // removes the const
- typedef T &reference;
-
- /// INTERNAL ONLY
- ///
- template<typename T2>
- static reference call(T2 &t)
- {
- return t;
- }
+ typedef typename Domain::template as_expr<T>::result_type type;
};
/// \brief A metafunction that computes the return type of the \c as_child()
/// function.
- ///
- /// The <tt>as_child\<\></tt> metafunction turns types into Proto types, if
- /// they are not already, by making them Proto terminals held by reference.
- /// Types which are already Proto types are returned by reference.
- ///
- /// This specialization is selected when the type is not yet a Proto type.
- /// The result type <tt>as_child\<T, Domain\>::type</tt> is
- /// <tt>boost::result_of\<Domain(expr\< tag::terminal, term\<T &\> \>)\>::type</tt>.
- template<
- typename T
- , typename Domain // = default_domain
- , typename Void // = void
- #ifdef BOOST_PROTO_BROKEN_PTS
- , typename Void2 // = void
- #endif
- >
+ template<typename T, typename Domain /*= default_domain*/>
struct as_child
{
- typedef typename base_expr<Domain, proto::tag::terminal, term<T &> >::type expr_;
- typedef typename Domain::proto_generator proto_generator;
- typedef typename proto_generator::template result<proto_generator(expr_)>::type type;
-
- /// INTERNAL ONLY
- ///
- template<typename T2>
- static type call(T2 &t)
- {
- return proto_generator()(expr_::make(static_cast<T &>(t)));
- }
- };
-
- /// \brief A metafunction that computes the return type of the \c as_child()
- /// function.
- ///
- /// The <tt>as_child\<\></tt> metafunction turns types into Proto types, if
- /// they are not already, by making them Proto terminals held by reference.
- /// Types which are already Proto types are returned by reference.
- ///
- /// This specialization is selected when the type is already a Proto type.
- /// The result type <tt>as_child\<T, Domain\>::type</tt> is
- /// <tt>T &</tt>.
- template<typename T, typename Domain>
- struct as_child<
- T
- , Domain
- , typename T::proto_is_expr_
- #ifdef BOOST_PROTO_BROKEN_PTS
- , typename disable_if<is_same<Domain, typename T::proto_domain> >::type
- #endif
- >
- {
- typedef typename Domain::proto_generator proto_generator;
- // BUGBUG should be able to hold this guy by reference, no?
- #if BOOST_WORKAROUND(BOOST_MSVC, == 1310) || \
- BOOST_WORKAROUND(BOOST_INTEL, BOOST_TESTED_AT(1010))
- // These compilers don't strip top-level cv qualifiers
- // on arguments in function types
- typedef
- typename proto_generator::template result<
- proto_generator(typename T::proto_derived_expr)
- >::type
- type;
- #else
- typedef typename proto_generator::template result<proto_generator(T)>::type type;
- #endif
-
- /// INTERNAL ONLY
- ///
- template<typename T2>
- static type call(T2 &t)
- {
- return proto_generator()(static_cast<T &>(t));
- }
- };
-
- /// \brief A metafunction that computes the return type of the \c as_child()
- /// function.
- ///
- /// The <tt>as_child\<\></tt> metafunction turns types into Proto types, if
- /// they are not already, by making them Proto terminals held by reference.
- /// Types which are already Proto types are returned by reference.
- ///
- /// This specialization is selected when the type is already a Proto type.
- /// The result type <tt>as_child\<T, Domain\>::type</tt> is
- /// <tt>T &</tt>.
- template<typename T>
- struct as_child<
- T
- , typename T::proto_domain
- , typename T::proto_is_expr_
- #ifdef BOOST_PROTO_BROKEN_PTS
- , void
- #endif
- >
- {
- typedef T &type;
-
- /// INTERNAL ONLY
- ///
- template<typename T2>
- static type call(T2 &t)
- {
- return static_cast<T &>(t);
- }
+ typedef typename Domain::template as_child<T>::result_type type;
};
/// \brief A metafunction that returns the type of the Nth child
@@ -514,10 +309,6 @@
typedef typename detail::term_traits<typename Expr::proto_child0>::const_reference type;
};
- // TODO left<> and right<> force the instantiation of Expr.
- // Couldn't we partially specialize them on proto::expr< T, A >
- // and return A::child0 / A::child1?
-
/// \brief A metafunction that returns the type of the left child
/// of a binary Proto expression.
///
@@ -814,47 +605,49 @@
template<typename This, typename T>
struct result<This(T)>
- : result_of::as_expr<T, Domain>
- {};
+ {
+ typedef typename Domain::template as_expr<T>::result_type type;
+ };
template<typename This, typename T>
struct result<This(T &)>
- : result_of::as_expr<T, Domain>
- {};
+ {
+ typedef typename Domain::template as_expr<T>::result_type type;
+ };
/// \brief Wrap an object in a Proto terminal if it isn't a
/// Proto expression already.
/// \param t The object to wrap.
/// \return <tt>proto::as_expr\<Domain\>(t)</tt>
template<typename T>
- typename result_of::as_expr<T, Domain>::reference
+ typename Domain::template as_expr<T>::result_type
operator ()(T &t) const
{
- return result_of::as_expr<T, Domain>::call(t);
+ return typename Domain::template as_expr<T>()(t);
}
/// \overload
///
template<typename T>
- typename result_of::as_expr<T const, Domain>::reference
+ typename Domain::template as_expr<T const>::result_type
operator ()(T const &t) const
{
- return result_of::as_expr<T const, Domain>::call(t);
+ return typename Domain::template as_expr<T const>()(t);
}
#if BOOST_WORKAROUND(BOOST_MSVC, == 1310)
template<typename T, std::size_t N_>
- typename result_of::as_expr<T[N_], Domain>::reference
+ typename Domain::template as_expr<T[N_]>::result_type
operator ()(T (&t)[N_]) const
{
- return result_of::as_expr<T[N_], Domain>::call(t);
+ return typename Domain::template as_expr<T[N_]>()(t);
}
template<typename T, std::size_t N_>
- typename result_of::as_expr<T const[N_], Domain>::reference
+ typename Domain::template as_expr<T const[N_]>::result_type
operator ()(T const (&t)[N_]) const
{
- return result_of::as_expr<T const[N_], Domain>::call(t);
+ return typename Domain::template as_expr<T const[N_]>()(t);
}
#endif
};
@@ -871,32 +664,34 @@
template<typename This, typename T>
struct result<This(T)>
- : result_of::as_child<T, Domain>
- {};
+ {
+ typedef typename Domain::template as_child<T>::result_type type;
+ };
template<typename This, typename T>
struct result<This(T &)>
- : result_of::as_child<T, Domain>
- {};
+ {
+ typedef typename Domain::template as_child<T>::result_type type;
+ };
/// \brief Wrap an object in a Proto terminal if it isn't a
/// Proto expression already.
/// \param t The object to wrap.
/// \return <tt>proto::as_child\<Domain\>(t)</tt>
template<typename T>
- typename result_of::as_child<T, Domain>::type
+ typename Domain::template as_child<T>::result_type
operator ()(T &t) const
{
- return result_of::as_child<T, Domain>::call(t);
+ return typename Domain::template as_child<T>()(t);
}
/// \overload
///
template<typename T>
- typename result_of::as_child<T const, Domain>::type
+ typename Domain::template as_child<T const>::result_type
operator ()(T const &t) const
{
- return result_of::as_child<T const, Domain>::call(t);
+ return typename Domain::template as_child<T const>()(t);
}
};
@@ -1118,37 +913,37 @@
///
/// \param t The object to wrap.
template<typename T>
- typename result_of::as_expr<T>::reference
+ typename default_domain::as_expr<T>::result_type
as_expr(T &t BOOST_PROTO_DISABLE_IF_IS_CONST(T) BOOST_PROTO_DISABLE_IF_IS_FUNCTION(T))
{
- return result_of::as_expr<T>::call(t);
+ return default_domain::as_expr<T>()(t);
}
/// \overload
///
template<typename T>
- typename result_of::as_expr<T const>::reference
+ typename default_domain::as_expr<T const>::result_type
as_expr(T const &t)
{
- return result_of::as_expr<T const>::call(t);
+ return default_domain::as_expr<T const>()(t);
}
/// \overload
///
template<typename Domain, typename T>
- typename result_of::as_expr<T, Domain>::reference
+ typename Domain::template as_expr<T>::result_type
as_expr(T &t BOOST_PROTO_DISABLE_IF_IS_CONST(T) BOOST_PROTO_DISABLE_IF_IS_FUNCTION(T))
{
- return result_of::as_expr<T, Domain>::call(t);
+ return typename Domain::template as_expr<T>()(t);
}
/// \overload
///
template<typename Domain, typename T>
- typename result_of::as_expr<T const, Domain>::reference
+ typename Domain::template as_expr<T const>::result_type
as_expr(T const &t)
{
- return result_of::as_expr<T const, Domain>::call(t);
+ return typename Domain::template as_expr<T const>()(t);
}
/// \brief A function that wraps non-Proto expression types in Proto
@@ -1171,37 +966,37 @@
///
/// \param t The object to wrap.
template<typename T>
- typename result_of::as_child<T>::type
+ typename default_domain::as_child<T>::result_type
as_child(T &t BOOST_PROTO_DISABLE_IF_IS_CONST(T) BOOST_PROTO_DISABLE_IF_IS_FUNCTION(T))
{
- return result_of::as_child<T>::call(t);
+ return default_domain::as_child<T>()(t);
}
/// \overload
///
template<typename T>
- typename result_of::as_child<T const>::type
+ typename default_domain::as_child<T const>::result_type
as_child(T const &t)
{
- return result_of::as_child<T const>::call(t);
+ return default_domain::as_child<T const>()(t);
}
/// \overload
///
template<typename Domain, typename T>
- typename result_of::as_child<T, Domain>::type
+ typename Domain::template as_child<T>::result_type
as_child(T &t BOOST_PROTO_DISABLE_IF_IS_CONST(T) BOOST_PROTO_DISABLE_IF_IS_FUNCTION(T))
{
- return result_of::as_child<T, Domain>::call(t);
+ return typename Domain::template as_child<T>()(t);
}
/// \overload
///
template<typename Domain, typename T>
- typename result_of::as_child<T const, Domain>::type
+ typename Domain::template as_child<T const>::result_type
as_child(T const &t)
{
- return result_of::as_child<T const, Domain>::call(t);
+ return typename Domain::template as_child<T const>()(t);
}
/// \brief Return the Nth child of the specified Proto expression.
Modified: trunk/libs/proto/doc/reference/literal.xml
==============================================================================
--- trunk/libs/proto/doc/reference/literal.xml (original)
+++ trunk/libs/proto/doc/reference/literal.xml 2010-06-10 10:07:00 EDT (Thu, 10 Jun 2010)
@@ -20,7 +20,7 @@
</template>
<inherit>
<type>
- <classname>proto::extends</classname><typename <classname>proto::terminal</classname><T>::type, proto::literal<T, Domain>, Domain></type>
+ <classname>proto::extends</classname><<classname>proto::basic_expr</classname><<classname>proto::tag::terminal</classname>, <classname>proto::term</classname>< T > >, proto::literal<T, Domain>, Domain></type>
</inherit>
<purpose>A simple wrapper for a terminal, provided for ease of use.</purpose>
<description>
@@ -36,7 +36,7 @@
</description>
<typedef name="X">
<purpose>For exposition only</purpose>
- <type>typename <classname>proto::terminal</classname><T>::type</type>
+ <type><classname>proto::basic_expr</classname><<classname>proto::tag::terminal</classname>, <classname>proto::term</classname>< T > ></type>
</typedef>
<typedef name="value_type">
<type>typename <classname>proto::result_of::value</classname><X>::type</type>
Boost-Commit list run by bdawes at acm.org, david.abrahams at rcn.com, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk