matches.hpp

来自「Boost provides free peer-reviewed portab」· HPP 代码 · 共 996 行 · 第 1/3 页

HPP
996
字号
                typename Args1::BOOST_PP_CAT(arg, n)::proto_base_expr\              , typename Args2::BOOST_PP_CAT(arg, n)::proto_base_expr\            >        #define BOOST_PROTO_DEFINE_MATCHES(z, n, data)\            matches_<\                typename Expr::proto_base_expr\              , typename BOOST_PP_CAT(G, n)::proto_base_expr\            >        #define BOOST_PROTO_DEFINE_LAMBDA_MATCHES(z, n, data)\            lambda_matches<\                BOOST_PP_CAT(Expr, n)\              , BOOST_PP_CAT(Grammar, n)\            >        #if BOOST_PROTO_MAX_LOGICAL_ARITY > BOOST_PROTO_MAX_ARITY            #define BOOST_PP_ITERATION_PARAMS_1 (4, (2, BOOST_PROTO_MAX_LOGICAL_ARITY, <boost/xpressive/proto/matches.hpp>, 1))        #else            #define BOOST_PP_ITERATION_PARAMS_1 (4, (2, BOOST_PROTO_MAX_ARITY, <boost/xpressive/proto/matches.hpp>, 1))        #endif        #include BOOST_PP_ITERATE()        #define BOOST_PP_ITERATION_PARAMS_1 (4, (2, BOOST_PROTO_MAX_ARITY, <boost/xpressive/proto/matches.hpp>, 2))        #include BOOST_PP_ITERATE()        #undef BOOST_PROTO_MATCHES_N_FUN        #undef BOOST_PROTO_DEFINE_MATCHES        #undef BOOST_PROTO_DEFINE_LAMBDA_MATCHES            // handle proto::if_            template<typename Expr, typename If, typename Then, typename Else>            struct matches_<Expr, proto::if_<If, Then, Else> >              : mpl::eval_if<                    typename when<_, If>::template result<void(Expr, int, int)>::type                  , matches_<Expr, typename Then::proto_base_expr>                  , matches_<Expr, typename Else::proto_base_expr>                >::type            {};            template<typename Expr, typename If>            struct matches_<Expr, proto::if_<If> >              : when<_, If>::template result<void(Expr, int, int)>::type            {};            // handle proto::not_            template<typename Expr, typename Grammar>            struct matches_<Expr, not_<Grammar> >              : mpl::not_<matches_<Expr, typename Grammar::proto_base_expr> >            {};            // handle proto::switch_            template<typename Expr, typename Cases>            struct matches_<Expr, switch_<Cases> >              : matches_<                    Expr                  , typename Cases::template case_<typename Expr::proto_tag>::proto_base_expr                >            {};        }        namespace result_of        {            /// \brief A Boolean metafunction that evaluates whether a given            /// expression type matches a grammar.            ///            /// <tt>matches\<Expr,Grammar\></tt> inherits (indirectly) from            /// \c mpl::true_ if <tt>Expr::proto_base_expr</tt> matches            /// <tt>Grammar::proto_base_expr</tt>, and from \c mpl::false_            /// otherwise.            ///            /// Non-terminal expressions are matched against a grammar            /// according to the following rules:            ///            /// \li The wildcard pattern, \c _, matches any expression.            /// \li An expression <tt>expr\<AT, argsN\<A0,A1,...An\> \></tt>            ///     matches a grammar <tt>expr\<BT, argsN\<B0,B1,...Bn\> \></tt>            ///     if \c BT is \c _ or \c AT, and if \c Ax matches \c Bx for            ///     each \c x in <tt>[0,n)</tt>.            /// \li An expression <tt>expr\<AT, argsN\<A0,...An,U0,...Um\> \></tt>            ///     matches a grammar <tt>expr\<BT, argsM\<B0,...Bn,vararg\<V\> \> \></tt>            ///     if \c BT is \c _ or \c AT, and if \c Ax matches \c Bx            ///     for each \c x in <tt>[0,n)</tt> and if \c Ux matches \c V            ///     for each \c x in <tt>[0,m)</tt>.            /// \li An expression \c E matches <tt>or_\<B0,B1,...Bn\></tt> if \c E            ///     matches some \c Bx for \c x in <tt>[0,n)</tt>.            /// \li An expression \c E matches <tt>and_\<B0,B1,...Bn\></tt> if \c E            ///     matches all \c Bx for \c x in <tt>[0,n)</tt>.            /// \li An expression \c E matches <tt>if_\<T,U,V\></tt> if            ///     <tt>when\<_,T\>::::result\<void(E,int,int)\>::::type::value</tt>            ///     is \c true and \c E matches \c U; or, if            ///     <tt>when\<_,T\>::::result\<void(E,int,int)\>::::type::value</tt>            ///     is \c false and \c E matches \c V. (Note: \c U defaults to \c _            ///     and \c V defaults to \c not_\<_\>.)            /// \li An expression \c E matches <tt>not_\<T\></tt> if \c E does            ///     not match \c T.            /// \li An expression \c E matches <tt>switch_\<C\></tt> if            ///     \c E matches <tt>C::case_\<E::proto_tag\></tt>.            ///            /// A terminal expression <tt>expr\<tag::terminal,args0\<A\> \></tt> matches            /// a grammar <tt>expr\<BT,args0\<B\> \></tt> if \c BT is \c _ or            /// \c tag::terminal and one of the following is true:            ///            /// \li \c B is the wildcard pattern, \c _            /// \li \c A is \c B            /// \li \c A is <tt>B &</tt>            /// \li \c A is <tt>B const &</tt>            /// \li \c B is <tt>exact\<A\></tt>            /// \li \c B is <tt>convertible_to\<X\></tt> and            ///     <tt>is_convertible\<A,X\>::::value</tt> is \c true.            /// \li \c A is <tt>X[M]</tt> or <tt>X(&)[M]</tt> and            ///     \c B is <tt>X[proto::N]</tt>.            /// \li \c A is <tt>X(&)[M]</tt> and \c B is <tt>X(&)[proto::N]</tt>.            /// \li \c A is <tt>X[M]</tt> or <tt>X(&)[M]</tt> and            ///     \c B is <tt>X*</tt>.            /// \li \c B lambda-matches \c A (see below).            ///            /// A type \c B lambda-matches \c A if one of the following is true:            ///            /// \li \c B is \c A            /// \li \c B is the wildcard pattern, \c _            /// \li \c B is <tt>T\<B0,B1,...Bn\></tt> and \c A is            ///     <tt>T\<A0,A1,...An\></tt> and for each \c x in            ///     <tt>[0,n)</tt>, \c Ax and \c Bx are types            ///     such that \c Ax lambda-matches \c Bx             template<typename Expr, typename Grammar>            struct matches              : detail::matches_<                    typename Expr::proto_base_expr                  , typename Grammar::proto_base_expr                >            {};        }        namespace wildcardns_        {            /// \brief A wildcard grammar element that matches any expression,            /// and a transform that returns the current expression unchanged.            ///             /// The wildcard type, \c _, is a grammar element such that            /// <tt>matches\<E,_\>::::value</tt> is \c true for any expression            /// type \c E.            ///            /// The wildcard can also be used as a stand-in for a template            /// argument when matching terminals. For instance, the following            /// is a grammar that will match any <tt>std::complex\<\></tt>            /// terminal:            ///            /// \code            /// BOOST_MPL_ASSERT((            ///     matches<            ///         terminal<std::complex<double> >::type            ///       , terminal<std::complex< _ > >            ///     >            /// ));            /// \endcode            ///            /// When used as a transform, \c _ returns the current expression            /// unchanged. For instance, in the following, \c _ is used with            /// the \c fold\<\> transform to fold the children of a node:            ///            /// \code            /// struct CountChildren            ///   : or_<            ///         // Terminals have no children            ///         when<terminal<_>, mpl::int_<0>()>            ///         // Use fold<> to count the children of non-terminals            ///       , otherwise<            ///             fold<            ///                 _ // <-- fold the current expression            ///               , mpl::int_<0>()            ///               , mpl::plus<_state, mpl::int_<1> >()            ///             >            ///         >            ///     >            /// {};            /// \endcode            struct _ : proto::callable            {                typedef _ proto_base_expr;                template<typename Sig>                struct result;                template<typename This, typename Expr, typename State, typename Visitor>                struct result<This(Expr, State, Visitor)>                {                    typedef Expr type;                };                /// \param expr An expression                /// \return \c expr                template<typename Expr, typename State, typename Visitor>                Expr const &operator ()(Expr const &expr, State const &, Visitor &) const                {                    return expr;                }            };        }        namespace control        {            /// \brief Inverts the set of expressions matched by a grammar. When            /// used as a transform, \c not_\<\> returns the current expression            /// unchanged.            ///            /// If an expression type \c E does not match a grammar \c G, then            /// \c E \e does match <tt>not_\<G\></tt>. For example,            /// <tt>not_\<terminal\<_\> \></tt> will match any non-terminal.            template<typename Grammar>            struct not_ : proto::callable            {                typedef not_ proto_base_expr;                template<typename Sig>                struct result;                template<typename This, typename Expr, typename State, typename Visitor>                struct result<This(Expr, State, Visitor)>                {                    typedef Expr type;                };                /// \param expr An expression                /// \pre <tt>matches\<Expr,not_\>::::value</tt> is \c true.                /// \return \c expr                template<typename Expr, typename State, typename Visitor>                Expr const &operator ()(Expr const &expr, State const &, Visitor &) const                {                    return expr;                }            };            /// \brief Used to select one grammar or another based on the result            /// of a compile-time Boolean. When used as a transform, \c if_\<\>            /// selects between two transforms based on a compile-time Boolean.            ///            /// When <tt>if_\<If,Then,Else\></tt> is used as a grammar, \c If            /// must be a Proto transform and \c Then and \c Else must be grammars.            /// An expression type \c E matches <tt>if_\<If,Then,Else\></tt> if            /// <tt>when\<_,If\>::::result\<void(E,int,int)\>::::type::value</tt>            /// is \c true and \c E matches \c U; or, if            /// <tt>when\<_,If\>::::result\<void(E,int,int)\>::::type::value</tt>            /// is \c false and \c E matches \c V.            ///            /// The template parameter \c Then defaults to \c _            /// and \c Else defaults to \c not\<_\>, so an expression type \c E            /// will match <tt>if_\<If\></tt> if and only if            /// <tt>when\<_,If\>::::result\<void(E,int,int)\>::::type::value</tt>            /// is \c true.            ///            /// \code            /// // A grammar that only matches integral terminals,            /// // using is_integral<> from Boost.Type_traits.            /// struct IsIntegral            ///   : and_<            ///         terminal<_>            ///       , if_< is_integral<_arg>() >            ///     >            /// {};            /// \endcode            ///            /// When <tt>if_\<If,Then,Else\></tt> is used as a transform, \c If,            /// \c Then and \c Else must be Proto transforms. When applying            /// the transform to an expression \c E, state \c S and visitor \c V,            /// if <tt>when\<_,If\>::::result\<void(E,S,V)\>::::type::value</tt>            /// is \c true then the \c Then transform is applied; otherwise            /// the \c Else transform is applied.            ///            /// \code            /// // Match a terminal. If the terminal is integral, return            /// // mpl::true_; otherwise, return mpl::false_.            /// struct IsIntegral2            ///   : when<            ///         terminal<_>            ///       , if_<            ///             is_integral<_arg>()            ///           , mpl::true_()            ///           , mpl::false_()            ///         >            ///     >            /// {};            /// \endcode            template<                typename If              , typename Then   BOOST_PROTO_FOR_DOXYGEN_ONLY(= _)              , typename Else   BOOST_PROTO_FOR_DOXYGEN_ONLY(= not_<_>)            >            struct if_ : proto::callable            {                typedef if_ proto_base_expr;                template<typename Sig>                struct result;                template<typename This, typename Expr, typename State, typename Visitor>                struct result<This(Expr, State, Visitor)>                {                    typedef                        typename when<_, If>::template result<void(Expr, State, Visitor)>::type                    condition;                    typedef                        typename mpl::if_<                            condition                          , when<_, Then>                          , when<_, Else>                        >::type                    which;                    typedef typename which::template result<void(Expr, State, Visitor)>::type type;                };                /// \param expr An expression                /// \param state The current state                /// \param visitor A visitor of arbitrary type                /// \return <tt>result\<void(Expr, State, Visitor)\>::::which()(expr, state, visitor)</tt>                template<typename Expr, typename State, typename Visitor>                typename result<void(Expr, State, Visitor)>::type                operator ()(Expr const &expr, State const &state, Visitor &visitor) const                {                    typedef                        typename result<void(Expr, State, Visitor)>::which                    which;                    return which()(expr, state, visitor);                }            };            /// \brief For matching one of a set of alternate grammars. Alternates            /// tried in order to avoid ambiguity. When used as a transform, \c or_\<\>            /// applies the transform associated with the first grammar that matches

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?