Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-01-18 09:53:56

0001 // Copyright (C) 2016-2018 T. Zachary Laine
0002 //
0003 // Distributed under the Boost Software License, Version 1.0. (See
0004 // accompanying file LICENSE_1_0.txt or copy at
0005 // http://www.boost.org/LICENSE_1_0.txt)
0006 #ifndef BOOST_YAP_EXPRESSION_HPP_INCLUDED
0007 #define BOOST_YAP_EXPRESSION_HPP_INCLUDED
0008 
0009 #include <boost/yap/algorithm.hpp>
0010 
0011 
0012 namespace boost { namespace yap {
0013 
0014     /** Reference expression template that provides all operator overloads.
0015 
0016         \note Due to a limitation of Doxygen, each of the
0017         <code>value()</code>, <code>left()</code>, <code>right()</code>, and
0018         operator overloads listed here is a stand-in for three member
0019         functions.  For each function <code>f</code>, the listing here is:
0020         \code return_type f (); \endcode  However, there are actually three
0021         functions:
0022         \code
0023         return_type f () const &;
0024         return_type f () &;
0025         return_type f () &&;
0026         \endcode
0027     */
0028     template<expr_kind Kind, typename Tuple>
0029     struct expression
0030     {
0031         using tuple_type = Tuple;
0032 
0033         static const expr_kind kind = Kind;
0034 
0035         /** Default constructor.  Does nothing. */
0036         constexpr expression() {}
0037 
0038         /** Moves \a rhs into the only data mamber, \c elements. */
0039         constexpr expression(tuple_type && rhs) :
0040             elements(static_cast<tuple_type &&>(rhs))
0041         {}
0042 
0043         tuple_type elements;
0044 
0045         /** A convenience member function that dispatches to the free function
0046             <code>value()</code>. */
0047         constexpr decltype(auto) value() &
0048         {
0049             return ::boost::yap::value(*this);
0050         }
0051 
0052 #ifndef BOOST_YAP_DOXYGEN
0053 
0054         constexpr decltype(auto) value() const &
0055         {
0056             return ::boost::yap::value(*this);
0057         }
0058 
0059         constexpr decltype(auto) value() &&
0060         {
0061             return ::boost::yap::value(std::move(*this));
0062         }
0063 
0064 #endif
0065 
0066         /** A convenience member function that dispatches to the free function
0067             <code>left()</code>. */
0068         constexpr decltype(auto) left() & { return ::boost::yap::left(*this); }
0069 
0070 #ifndef BOOST_YAP_DOXYGEN
0071 
0072         constexpr decltype(auto) left() const &
0073         {
0074             return ::boost::yap::left(*this);
0075         }
0076 
0077         constexpr decltype(auto) left() &&
0078         {
0079             return ::boost::yap::left(std::move(*this));
0080         }
0081 
0082 #endif
0083 
0084         /** A convenience member function that dispatches to the free function
0085             <code>right()</code>. */
0086         constexpr decltype(auto) right() &
0087         {
0088             return ::boost::yap::right(*this);
0089         }
0090 
0091 #ifndef BOOST_YAP_DOXYGEN
0092 
0093         constexpr decltype(auto) right() const &
0094         {
0095             return ::boost::yap::right(*this);
0096         }
0097 
0098         constexpr decltype(auto) right() &&
0099         {
0100             return ::boost::yap::right(std::move(*this));
0101         }
0102 
0103 #endif
0104 
0105         BOOST_YAP_USER_ASSIGN_OPERATOR(
0106             expression, ::boost::yap::expression)                   // =
0107         BOOST_YAP_USER_SUBSCRIPT_OPERATOR(::boost::yap::expression) // []
0108         BOOST_YAP_USER_CALL_OPERATOR(::boost::yap::expression)      // ()
0109     };
0110 
0111     /** Terminal expression specialization of the reference expression
0112         template.
0113 
0114         \note Due to a limitation of Doxygen, the <code>value()</code> member
0115         and each of the operator overloads listed here is a stand-in for three
0116         member functions.  For each function <code>f</code>, the listing here
0117         is: \code return_type f (); \endcode However, there are actually three
0118         functions:
0119         \code
0120         return_type f () const &;
0121         return_type f () &;
0122         return_type f () &&;
0123         \endcode
0124     */
0125     template<typename T>
0126     struct expression<expr_kind::terminal, hana::tuple<T>>
0127     {
0128         using tuple_type = hana::tuple<T>;
0129 
0130         static const expr_kind kind = expr_kind::terminal;
0131 
0132         /** Default constructor.  Does nothing. */
0133         constexpr expression() {}
0134 
0135         /** Forwards \a t into \c elements. */
0136         constexpr expression(T && t) : elements(static_cast<T &&>(t)) {}
0137 
0138         /** Copies \a rhs into the only data mamber, \c elements. */
0139         constexpr expression(hana::tuple<T> const & rhs) : elements(rhs) {}
0140 
0141         /** Moves \a rhs into the only data mamber, \c elements. */
0142         constexpr expression(hana::tuple<T> && rhs) : elements(std::move(rhs))
0143         {}
0144 
0145         tuple_type elements;
0146 
0147         /** A convenience member function that dispatches to the free function
0148             <code>value()</code>. */
0149         constexpr decltype(auto) value() &
0150         {
0151             return ::boost::yap::value(*this);
0152         }
0153 
0154 #ifndef BOOST_YAP_DOXYGEN
0155 
0156         constexpr decltype(auto) value() const &
0157         {
0158             return ::boost::yap::value(*this);
0159         }
0160 
0161         constexpr decltype(auto) value() &&
0162         {
0163             return ::boost::yap::value(std::move(*this));
0164         }
0165 
0166 #endif
0167 
0168         BOOST_YAP_USER_ASSIGN_OPERATOR(
0169             expression, ::boost::yap::expression)                   // =
0170         BOOST_YAP_USER_SUBSCRIPT_OPERATOR(::boost::yap::expression) // []
0171         BOOST_YAP_USER_CALL_OPERATOR(::boost::yap::expression)      // ()
0172     };
0173 
0174 #ifndef BOOST_YAP_DOXYGEN
0175 
0176     BOOST_YAP_USER_UNARY_OPERATOR(unary_plus, expression, expression)  // +
0177     BOOST_YAP_USER_UNARY_OPERATOR(negate, expression, expression)      // -
0178     BOOST_YAP_USER_UNARY_OPERATOR(dereference, expression, expression) // *
0179     BOOST_YAP_USER_UNARY_OPERATOR(complement, expression, expression)  // ~
0180     BOOST_YAP_USER_UNARY_OPERATOR(address_of, expression, expression)  // &
0181     BOOST_YAP_USER_UNARY_OPERATOR(logical_not, expression, expression) // !
0182     BOOST_YAP_USER_UNARY_OPERATOR(pre_inc, expression, expression)     // ++
0183     BOOST_YAP_USER_UNARY_OPERATOR(pre_dec, expression, expression)     // --
0184     BOOST_YAP_USER_UNARY_OPERATOR(post_inc, expression, expression)    // ++(int)
0185     BOOST_YAP_USER_UNARY_OPERATOR(post_dec, expression, expression)    // --(int)
0186 
0187     BOOST_YAP_USER_BINARY_OPERATOR(shift_left, expression, expression)         // <<
0188     BOOST_YAP_USER_BINARY_OPERATOR(shift_right, expression, expression)        // >>
0189     BOOST_YAP_USER_BINARY_OPERATOR(multiplies, expression, expression)         // *
0190     BOOST_YAP_USER_BINARY_OPERATOR(divides, expression, expression)            // /
0191     BOOST_YAP_USER_BINARY_OPERATOR(modulus, expression, expression)            // %
0192     BOOST_YAP_USER_BINARY_OPERATOR(plus, expression, expression)               // +
0193     BOOST_YAP_USER_BINARY_OPERATOR(minus, expression, expression)              // -
0194     BOOST_YAP_USER_BINARY_OPERATOR(less, expression, expression)               // <
0195     BOOST_YAP_USER_BINARY_OPERATOR(greater, expression, expression)            // >
0196     BOOST_YAP_USER_BINARY_OPERATOR(less_equal, expression, expression)         // <=
0197     BOOST_YAP_USER_BINARY_OPERATOR(greater_equal, expression, expression)      // >=
0198     BOOST_YAP_USER_BINARY_OPERATOR(equal_to, expression, expression)           // ==
0199     BOOST_YAP_USER_BINARY_OPERATOR(not_equal_to, expression, expression)       // !=
0200     BOOST_YAP_USER_BINARY_OPERATOR(logical_or, expression, expression)         // ||
0201     BOOST_YAP_USER_BINARY_OPERATOR(logical_and, expression, expression)        // &&
0202     BOOST_YAP_USER_BINARY_OPERATOR(bitwise_and, expression, expression)        // &
0203     BOOST_YAP_USER_BINARY_OPERATOR(bitwise_or, expression, expression)         // |
0204     BOOST_YAP_USER_BINARY_OPERATOR(bitwise_xor, expression, expression)        // ^
0205     BOOST_YAP_USER_BINARY_OPERATOR(comma, expression, expression)              // ,
0206     BOOST_YAP_USER_BINARY_OPERATOR(mem_ptr, expression, expression)            // ->*
0207     BOOST_YAP_USER_BINARY_OPERATOR(shift_left_assign, expression, expression)  // <<=
0208     BOOST_YAP_USER_BINARY_OPERATOR(shift_right_assign, expression, expression) // >>=
0209     BOOST_YAP_USER_BINARY_OPERATOR(multiplies_assign, expression, expression)  // *=
0210     BOOST_YAP_USER_BINARY_OPERATOR(divides_assign, expression, expression)     // /=
0211     BOOST_YAP_USER_BINARY_OPERATOR(modulus_assign, expression, expression)     // %=
0212     BOOST_YAP_USER_BINARY_OPERATOR(plus_assign, expression, expression)        // +=
0213     BOOST_YAP_USER_BINARY_OPERATOR(minus_assign, expression, expression)       // -=
0214     BOOST_YAP_USER_BINARY_OPERATOR(bitwise_and_assign, expression, expression) // &=
0215     BOOST_YAP_USER_BINARY_OPERATOR(bitwise_or_assign, expression, expression)  // |=
0216     BOOST_YAP_USER_BINARY_OPERATOR(bitwise_xor_assign, expression, expression) // ^=
0217 
0218     BOOST_YAP_USER_EXPR_IF_ELSE(expression)
0219 
0220 #else
0221 
0222     /** \see BOOST_YAP_USER_UNARY_OPERATOR for full semantics. */
0223     template<typename Expr>
0224     constexpr auto operator+(Expr &&);
0225     /** \see BOOST_YAP_USER_UNARY_OPERATOR for full semantics. */
0226     template<typename Expr>
0227     constexpr auto operator-(Expr &&);
0228     /** \see BOOST_YAP_USER_UNARY_OPERATOR for full semantics. */
0229     template<typename Expr>
0230     constexpr auto operator*(Expr &&);
0231     /** \see BOOST_YAP_USER_UNARY_OPERATOR for full semantics. */
0232     template<typename Expr>
0233     constexpr auto operator~(Expr &&);
0234     /** \see BOOST_YAP_USER_UNARY_OPERATOR for full semantics. */
0235     template<typename Expr>
0236     constexpr auto operator&(Expr &&);
0237     /** \see BOOST_YAP_USER_UNARY_OPERATOR for full semantics. */
0238     template<typename Expr>
0239     constexpr auto operator!(Expr &&);
0240     /** \see BOOST_YAP_USER_UNARY_OPERATOR for full semantics. */
0241     template<typename Expr>
0242     constexpr auto operator++(Expr &&);
0243     /** \see BOOST_YAP_USER_UNARY_OPERATOR for full semantics. */
0244     template<typename Expr>
0245     constexpr auto operator--(Expr &&);
0246     /** \see BOOST_YAP_USER_UNARY_OPERATOR for full semantics. */
0247     template<typename Expr>
0248     constexpr auto operator++(Expr &&, int);
0249     /** \see BOOST_YAP_USER_UNARY_OPERATOR for full semantics. */
0250     template<typename Expr>
0251     constexpr auto operator--(Expr &&, int);
0252 
0253     /** \see BOOST_YAP_USER_BINARY_OPERATOR for full semantics. */
0254     template<typename LExpr, typename RExpr>
0255     constexpr auto operator<<(LExpr && lhs, RExpr && rhs);
0256     /** \see BOOST_YAP_USER_BINARY_OPERATOR for full semantics. */
0257     template<typename LExpr, typename RExpr>
0258     constexpr auto operator>>(LExpr && lhs, RExpr && rhs);
0259     /** \see BOOST_YAP_USER_BINARY_OPERATOR for full semantics. */
0260     template<typename LExpr, typename RExpr>
0261     constexpr auto operator*(LExpr && lhs, RExpr && rhs);
0262     /** \see BOOST_YAP_USER_BINARY_OPERATOR for full semantics. */
0263     template<typename LExpr, typename RExpr>
0264     constexpr auto operator/(LExpr && lhs, RExpr && rhs);
0265     /** \see BOOST_YAP_USER_BINARY_OPERATOR for full semantics. */
0266     template<typename LExpr, typename RExpr>
0267     constexpr auto operator%(LExpr && lhs, RExpr && rhs);
0268     /** \see BOOST_YAP_USER_BINARY_OPERATOR for full semantics. */
0269     template<typename LExpr, typename RExpr>
0270     constexpr auto operator+(LExpr && lhs, RExpr && rhs);
0271     /** \see BOOST_YAP_USER_BINARY_OPERATOR for full semantics. */
0272     template<typename LExpr, typename RExpr>
0273     constexpr auto operator-(LExpr && lhs, RExpr && rhs);
0274     /** \see BOOST_YAP_USER_BINARY_OPERATOR for full semantics. */
0275     template<typename LExpr, typename RExpr>
0276     constexpr auto operator<(LExpr && lhs, RExpr && rhs);
0277     /** \see BOOST_YAP_USER_BINARY_OPERATOR for full semantics. */
0278     template<typename LExpr, typename RExpr>
0279     constexpr auto operator>(LExpr && lhs, RExpr && rhs);
0280     /** \see BOOST_YAP_USER_BINARY_OPERATOR for full semantics. */
0281     template<typename LExpr, typename RExpr>
0282     constexpr auto operator<=(LExpr && lhs, RExpr && rhs);
0283     /** \see BOOST_YAP_USER_BINARY_OPERATOR for full semantics. */
0284     template<typename LExpr, typename RExpr>
0285     constexpr auto operator>=(LExpr && lhs, RExpr && rhs);
0286     /** \see BOOST_YAP_USER_BINARY_OPERATOR for full semantics. */
0287     template<typename LExpr, typename RExpr>
0288     constexpr auto operator==(LExpr && lhs, RExpr && rhs);
0289     /** \see BOOST_YAP_USER_BINARY_OPERATOR for full semantics. */
0290     template<typename LExpr, typename RExpr>
0291     constexpr auto operator!=(LExpr && lhs, RExpr && rhs);
0292     /** \see BOOST_YAP_USER_BINARY_OPERATOR for full semantics. */
0293     template<typename LExpr, typename RExpr>
0294     constexpr auto operator||(LExpr && lhs, RExpr && rhs);
0295     /** \see BOOST_YAP_USER_BINARY_OPERATOR for full semantics. */
0296     template<typename LExpr, typename RExpr>
0297     constexpr auto operator&&(LExpr && lhs, RExpr && rhs);
0298     /** \see BOOST_YAP_USER_BINARY_OPERATOR for full semantics. */
0299     template<typename LExpr, typename RExpr>
0300     constexpr auto operator&(LExpr && lhs, RExpr && rhs);
0301     /** \see BOOST_YAP_USER_BINARY_OPERATOR for full semantics. */
0302     template<typename LExpr, typename RExpr>
0303     constexpr auto operator|(LExpr && lhs, RExpr && rhs);
0304     /** \see BOOST_YAP_USER_BINARY_OPERATOR for full semantics. */
0305     template<typename LExpr, typename RExpr>
0306     constexpr auto operator^(LExpr && lhs, RExpr && rhs);
0307 
0308     /** \see BOOST_YAP_USER_EXPR_IF_ELSE for full semantics. */
0309     template<typename Expr1, typename Expr2, typename Expr3>
0310     constexpr auto if_else(Expr1 && expr1, Expr2 && expr2, Expr3 && expr3);
0311 
0312 #endif
0313 
0314     /** Returns <code>make_expression<boost::yap::expression, Kind>(...)</code>.
0315      */
0316     template<expr_kind Kind, typename... T>
0317     constexpr auto make_expression(T &&... t)
0318     {
0319         return make_expression<expression, Kind>(static_cast<T &&>(t)...);
0320     }
0321 
0322     /** Returns <code>make_terminal<boost::yap::expression>(t)</code>. */
0323     template<typename T>
0324     constexpr auto make_terminal(T && t)
0325     {
0326         return make_terminal<expression>(static_cast<T &&>(t));
0327     }
0328 
0329     /** Returns <code>as_expr<boost::yap::expression>(t)</code>. */
0330     template<typename T>
0331     constexpr decltype(auto) as_expr(T && t)
0332     {
0333         return as_expr<expression>(static_cast<T &&>(t));
0334     }
0335 
0336 }}
0337 
0338 #endif