#ifndef BOOST_PP_IS_ITERATING
    ///////////////////////////////////////////////////////////////////////////////
    /// \file deep_copy.hpp
    /// Replace all nodes stored by reference by nodes stored by value.
    //
    //  Copyright 2008 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_DEEP_COPY_HPP_EAN_11_21_2006
    #define BOOST_PROTO_DEEP_COPY_HPP_EAN_11_21_2006

    #include <boost/preprocessor/cat.hpp>
    #include <boost/preprocessor/repetition/enum.hpp>
    #include <boost/preprocessor/iteration/iterate.hpp>
    #include <boost/mpl/if.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
    {
        namespace detail
        {
            template<typename Expr, long Arity = Expr::proto_arity_c>
            struct deep_copy_impl;

            template<typename Expr>
            struct deep_copy_impl<Expr, 0>
            {
                typedef
                    typename base_expr<
                        typename Expr::proto_domain
                      , tag::terminal
                      , term<typename term_traits<typename Expr::proto_child0>::value_type>
                    >::type
                expr_type;

                typedef typename Expr::proto_generator proto_generator;
                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_type::make(e.proto_base().child0));
                }
            };
        }

        namespace result_of
        {
            /// \brief A metafunction for calculating the return type
            /// of \c proto::deep_copy().
            ///
            /// A metafunction for calculating the return type
            /// of \c proto::deep_copy(). The type parameter \c Expr
            /// should be the type of a Proto expression tree.
            /// It should not be a reference type, nor should it
            /// be cv-qualified.
            template<typename Expr>
            struct deep_copy
            {
                typedef
                    typename detail::deep_copy_impl<
                        BOOST_PROTO_UNCVREF(Expr)
                    >::result_type
                type;
            };
        }

        namespace functional
        {
            /// \brief A PolymorphicFunctionObject type for deep-copying
            /// Proto expression trees.
            ///
            /// A PolymorphicFunctionObject type for deep-copying
            /// Proto expression trees. When a tree is deep-copied,
            /// all internal nodes and most terminals held by reference
            /// are instead held by value.
            ///
            /// \attention Terminals of reference-to-function type are
            /// left unchanged. Terminals of reference-to-array type are
            /// stored by value, which can cause a large amount of data
            /// to be passed by value and stored on the stack.
            struct deep_copy
            {
                BOOST_PROTO_CALLABLE()

                template<typename Sig>
                struct result;

                template<typename This, typename Expr>
                struct result<This(Expr)>
                {
                    typedef
                        typename detail::deep_copy_impl<
                            BOOST_PROTO_UNCVREF(Expr)
                        >::result_type
                    type;
                };

                /// \brief Deep-copies a Proto expression tree, turning all
                /// nodes and terminals held by reference into ones held by
                /// value.
                template<typename Expr>
                typename result_of::deep_copy<Expr>::type
                operator()(Expr const &e) const
                {
                    return proto::detail::deep_copy_impl<Expr>()(e, 0, 0);
                }
            };
        }

        /// \brief A function for deep-copying
        /// Proto expression trees.
        ///
        /// A function for deep-copying
        /// Proto expression trees. When a tree is deep-copied,
        /// all internal nodes and most terminals held by reference
        /// are instead held by value.
        ///
        /// \attention Terminals of reference-to-function type are
        /// left unchanged.
        ///
        /// \sa proto::functional::deep_copy.
        template<typename Expr>
        typename proto::result_of::deep_copy<Expr>::type
        deep_copy(Expr const &e)
        {
            return proto::detail::deep_copy_impl<Expr>()(e, 0, 0);
        }

        /// \brief A PrimitiveTransform for deep-copying
        /// Proto expression trees.
        ///
        /// A PrimitiveTransform for deep-copying
        /// Proto expression trees. When a tree is deep-copied,
        /// all internal nodes and most terminals held by reference
        /// are instead held by value.
        ///
        /// \attention Terminals of reference-to-function type are
        /// left unchanged.
        ///
        /// \sa proto::functional::deep_copy.
        struct _deep_copy
          : proto::transform<_deep_copy>
        {
            template<typename E, typename S, typename D>
            struct impl
              : detail::deep_copy_impl<BOOST_PROTO_UNCVREF(E)>
            {};
        };

        namespace detail
        {
        #define BOOST_PROTO_DEFINE_DEEP_COPY_TYPE(Z, N, DATA)                                       \
            typename deep_copy_impl<                                                                \
                typename remove_reference<                                                          \
                    typename Expr::BOOST_PP_CAT(proto_child, N)                                     \
                >::type::proto_derived_expr                                                         \
            >::result_type                                                                          \
            /**/

        #define BOOST_PROTO_DEFINE_DEEP_COPY_FUN(Z, N, DATA)                                        \
            proto::deep_copy(e.proto_base().BOOST_PP_CAT(child, N))                                 \
            /**/

        #define BOOST_PP_ITERATION_PARAMS_1 (3, (1, BOOST_PROTO_MAX_ARITY, <boost/proto/deep_copy.hpp>))
        #include BOOST_PP_ITERATE()

        #undef BOOST_PROTO_DEFINE_DEEP_COPY_FUN
        #undef BOOST_PROTO_DEFINE_DEEP_COPY_TYPE
        }

    }}

    #endif // BOOST_PROTO_COMPILER_DEEP_COPY_HPP_EAN_11_21_2006

#else

    #define N BOOST_PP_ITERATION()

            template<typename Expr>
            struct deep_copy_impl<Expr, N>
            {
                typedef
                    typename base_expr<
                        typename Expr::proto_domain
                      , typename Expr::proto_tag
                      , BOOST_PP_CAT(list, N)<
                            BOOST_PP_ENUM(N, BOOST_PROTO_DEFINE_DEEP_COPY_TYPE, ~)
                        >
                    >::type
                expr_type;

                typedef typename Expr::proto_generator proto_generator;
                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_type const that = {
                        BOOST_PP_ENUM(N, BOOST_PROTO_DEFINE_DEEP_COPY_FUN, ~)
                    };

                    return proto_generator()(that);
                }
            };

    #undef N

#endif
