| /*============================================================================= |
| Phoenix V1.2.1 |
| Copyright (c) 2001-2002 Joel de Guzman |
| |
| 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 PHOENIX_FUNCTIONS_HPP |
| #define PHOENIX_FUNCTIONS_HPP |
| |
| /////////////////////////////////////////////////////////////////////////////// |
| #include <boost/spirit/home/classic/phoenix/actor.hpp> |
| #include <boost/spirit/home/classic/phoenix/composite.hpp> |
| |
| /////////////////////////////////////////////////////////////////////////////// |
| namespace phoenix { |
| |
| /////////////////////////////////////////////////////////////////////////////// |
| // |
| // function class |
| // |
| // Lazy functions |
| // |
| // This class provides a mechanism for lazily evaluating functions. |
| // Syntactically, a lazy function looks like an ordinary C/C++ |
| // function. The function call looks the same. However, unlike |
| // ordinary functions, the actual function execution is deferred. |
| // (see actor.hpp, primitives.hpp and composite.hpp for an |
| // overview). For example here are sample factorial function calls: |
| // |
| // factorial(4) |
| // factorial(arg1) |
| // factorial(arg1 * 6) |
| // |
| // These functions are automatically lazily bound unlike ordinary |
| // function pointers or functor objects that need to be explicitly |
| // bound through the bind function (see binders.hpp). |
| // |
| // A lazy function works in conjunction with a user defined functor |
| // (as usual with a member operator()). Only special forms of |
| // functor objects are allowed. This is required to enable true |
| // polymorphism (STL style monomorphic functors and function |
| // pointers can still be used through the bind facility in |
| // binders.hpp). |
| // |
| // This special functor is expected to have a nested template class |
| // result<A...TN> (where N is the number of arguments of its |
| // member operator()). The nested template class result should have |
| // a typedef 'type' that reflects the return type of its member |
| // operator(). This is essentially a type computer that answers the |
| // metaprogramming question "Given arguments of type A...TN, what |
| // will be the operator()'s return type?". |
| // |
| // There is a special case for functors that accept no arguments. |
| // Such nullary functors are only required to define a typedef |
| // result_type that reflects the return type of its operator(). |
| // |
| // Here's an example of a simple functor that computes the |
| // factorial of a number: |
| // |
| // struct factorial_impl { |
| // |
| // template <typename Arg> |
| // struct result { typedef Arg type; }; |
| // |
| // template <typename Arg> |
| // Arg operator()(Arg n) const |
| // { return (n <= 0) ? 1 : n * this->operator()(n-1); } |
| // }; |
| // |
| // As can be seen, the functor can be polymorphic. Its arguments |
| // and return type are not fixed to a particular type. The example |
| // above for example, can handle any type as long as it can carry |
| // out the required operations (i.e. <=, * and -). |
| // |
| // We can now declare and instantiate a lazy 'factorial' function: |
| // |
| // function<factorial_impl> factorial; |
| // |
| // Invoking a lazy function 'factorial' does not immediately |
| // execute the functor factorial_impl. Instead, a composite (see |
| // composite.hpp) object is created and returned to the caller. |
| // Example: |
| // |
| // factorial(arg1) |
| // |
| // does nothing more than return a composite. A second function |
| // call will invoke the actual factorial function. Example: |
| // |
| // int i = 4; |
| // cout << factorial(arg1)(i); |
| // |
| // will print out "24". |
| // |
| // Take note that in certain cases (e.g. for functors with state), |
| // an instance may be passed on to the constructor. Example: |
| // |
| // function<factorial_impl> factorial(ftor); |
| // |
| // where ftor is an instance of factorial_impl (this is not |
| // necessary in this case since factorial is a simple stateless |
| // functor). Take care though when using functors with state |
| // because the functors are taken in by value. It is best to keep |
| // the data manipulated by a functor outside the functor itself and |
| // keep a reference to this data inside the functor. Also, it is |
| // best to keep functors as small as possible. |
| // |
| /////////////////////////////////////////////////////////////////////////////// |
| template <typename OperationT> |
| struct function { |
| |
| function() : op() {} |
| function(OperationT const& op_) : op(op_) {} |
| |
| actor<composite<OperationT> > |
| operator()() const; |
| |
| template <typename A> |
| typename impl::make_composite<OperationT, A>::type |
| operator()(A const& a) const; |
| |
| template <typename A, typename B> |
| typename impl::make_composite<OperationT, A, B>::type |
| operator()(A const& a, B const& b) const; |
| |
| template <typename A, typename B, typename C> |
| typename impl::make_composite<OperationT, A, B, C>::type |
| operator()(A const& a, B const& b, C const& c) const; |
| |
| #if PHOENIX_LIMIT > 3 |
| |
| template <typename A, typename B, typename C, typename D> |
| typename impl::make_composite<OperationT, A, B, C, D>::type |
| operator()(A const& a, B const& b, C const& c, D const& d) const; |
| |
| template <typename A, typename B, typename C, typename D, typename E> |
| typename impl::make_composite< |
| OperationT, A, B, C, D, E |
| >::type |
| operator()( |
| A const& a, B const& b, C const& c, D const& d, E const& e |
| ) const; |
| |
| template < |
| typename A, typename B, typename C, typename D, typename E, |
| typename F |
| > |
| typename impl::make_composite< |
| OperationT, A, B, C, D, E, F |
| >::type |
| operator()( |
| A const& a, B const& b, C const& c, D const& d, E const& e, |
| F const& f |
| ) const; |
| |
| #if PHOENIX_LIMIT > 6 |
| |
| template < |
| typename A, typename B, typename C, typename D, typename E, |
| typename F, typename G |
| > |
| typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G |
| >::type |
| operator()( |
| A const& a, B const& b, C const& c, D const& d, E const& e, |
| F const& f, G const& g |
| ) const; |
| |
| template < |
| typename A, typename B, typename C, typename D, typename E, |
| typename F, typename G, typename H |
| > |
| typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H |
| >::type |
| operator()( |
| A const& a, B const& b, C const& c, D const& d, E const& e, |
| F const& f, G const& g, H const& h |
| ) const; |
| |
| template < |
| typename A, typename B, typename C, typename D, typename E, |
| typename F, typename G, typename H, typename I |
| > |
| typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H, I |
| >::type |
| operator()( |
| A const& a, B const& b, C const& c, D const& d, E const& e, |
| F const& f, G const& g, H const& h, I const& i |
| ) const; |
| |
| #if PHOENIX_LIMIT > 9 |
| |
| template < |
| typename A, typename B, typename C, typename D, typename E, |
| typename F, typename G, typename H, typename I, typename J |
| > |
| typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H, I, J |
| >::type |
| operator()( |
| A const& a, B const& b, C const& c, D const& d, E const& e, |
| F const& f, G const& g, H const& h, I const& i, J const& j |
| ) const; |
| |
| template < |
| typename A, typename B, typename C, typename D, typename E, |
| typename F, typename G, typename H, typename I, typename J, |
| typename K |
| > |
| typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H, I, J, K |
| >::type |
| operator()( |
| A const& a, B const& b, C const& c, D const& d, E const& e, |
| F const& f, G const& g, H const& h, I const& i, J const& j, |
| K const& k |
| ) const; |
| |
| template < |
| typename A, typename B, typename C, typename D, typename E, |
| typename F, typename G, typename H, typename I, typename J, |
| typename K, typename L |
| > |
| typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H, I, J, K, L |
| >::type |
| operator()( |
| A const& a, B const& b, C const& c, D const& d, E const& e, |
| F const& f, G const& g, H const& h, I const& i, J const& j, |
| K const& k, L const& l |
| ) const; |
| |
| #if PHOENIX_LIMIT > 12 |
| |
| template < |
| typename A, typename B, typename C, typename D, typename E, |
| typename F, typename G, typename H, typename I, typename J, |
| typename K, typename L, typename M |
| > |
| typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H, I, J, K, L, M |
| >::type |
| operator()( |
| A const& a, B const& b, C const& c, D const& d, E const& e, |
| F const& f, G const& g, H const& h, I const& i, J const& j, |
| K const& k, L const& l, M const& m |
| ) const; |
| |
| template < |
| typename A, typename B, typename C, typename D, typename E, |
| typename F, typename G, typename H, typename I, typename J, |
| typename K, typename L, typename M, typename N |
| > |
| typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H, I, J, K, L, M, N |
| >::type |
| operator()( |
| A const& a, B const& b, C const& c, D const& d, E const& e, |
| F const& f, G const& g, H const& h, I const& i, J const& j, |
| K const& k, L const& l, M const& m, N const& n |
| ) const; |
| |
| template < |
| typename A, typename B, typename C, typename D, typename E, |
| typename F, typename G, typename H, typename I, typename J, |
| typename K, typename L, typename M, typename N, typename O |
| > |
| typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H, I, J, K, L, M, N, O |
| >::type |
| operator()( |
| A const& a, B const& b, C const& c, D const& d, E const& e, |
| F const& f, G const& g, H const& h, I const& i, J const& j, |
| K const& k, L const& l, M const& m, N const& n, O const& o |
| ) const; |
| |
| #endif |
| #endif |
| #endif |
| #endif |
| |
| OperationT op; |
| }; |
| |
| /////////////////////////////////////////////////////////////////////////////// |
| // |
| // function class implementation |
| // |
| /////////////////////////////////////////////////////////////////////////////// |
| template <typename OperationT> |
| inline actor<composite<OperationT> > |
| function<OperationT>::operator()() const |
| { |
| return actor<composite<OperationT> >(op); |
| } |
| |
| ////////////////////////////////// |
| template <typename OperationT> |
| template <typename A> |
| inline typename impl::make_composite<OperationT, A>::type |
| function<OperationT>::operator()(A const& a) const |
| { |
| typedef typename impl::make_composite<OperationT, A>::composite_type ret_t; |
| return ret_t |
| ( |
| op, |
| as_actor<A>::convert(a) |
| ); |
| } |
| |
| ////////////////////////////////// |
| template <typename OperationT> |
| template <typename A, typename B> |
| inline typename impl::make_composite<OperationT, A, B>::type |
| function<OperationT>::operator()(A const& a, B const& b) const |
| { |
| typedef |
| typename impl::make_composite<OperationT, A, B>::composite_type |
| ret_t; |
| |
| return ret_t( |
| op, |
| as_actor<A>::convert(a), |
| as_actor<B>::convert(b) |
| ); |
| } |
| |
| ////////////////////////////////// |
| template <typename OperationT> |
| template <typename A, typename B, typename C> |
| inline typename impl::make_composite<OperationT, A, B, C>::type |
| function<OperationT>::operator()(A const& a, B const& b, C const& c) const |
| { |
| typedef |
| typename impl::make_composite<OperationT, A, B, C>::composite_type |
| ret_t; |
| |
| return ret_t( |
| op, |
| as_actor<A>::convert(a), |
| as_actor<B>::convert(b), |
| as_actor<C>::convert(c) |
| ); |
| } |
| |
| #if PHOENIX_LIMIT > 3 |
| ////////////////////////////////// |
| template <typename OperationT> |
| template < |
| typename A, typename B, typename C, typename D |
| > |
| inline typename impl::make_composite< |
| OperationT, A, B, C, D |
| >::type |
| function<OperationT>::operator()( |
| A const& a, B const& b, C const& c, D const& d |
| ) const |
| { |
| typedef typename impl::make_composite< |
| OperationT, A, B, C, D |
| >::composite_type ret_t; |
| |
| return ret_t( |
| op, |
| as_actor<A>::convert(a), |
| as_actor<B>::convert(b), |
| as_actor<C>::convert(c), |
| as_actor<D>::convert(d) |
| ); |
| } |
| |
| ////////////////////////////////// |
| template <typename OperationT> |
| template < |
| typename A, typename B, typename C, typename D, typename E |
| > |
| inline typename impl::make_composite< |
| OperationT, A, B, C, D, E |
| >::type |
| function<OperationT>::operator()( |
| A const& a, B const& b, C const& c, D const& d, E const& e |
| ) const |
| { |
| typedef typename impl::make_composite< |
| OperationT, A, B, C, D, E |
| >::composite_type ret_t; |
| |
| return ret_t( |
| op, |
| as_actor<A>::convert(a), |
| as_actor<B>::convert(b), |
| as_actor<C>::convert(c), |
| as_actor<D>::convert(d), |
| as_actor<E>::convert(e) |
| ); |
| } |
| |
| ////////////////////////////////// |
| template <typename OperationT> |
| template < |
| typename A, typename B, typename C, typename D, typename E, |
| typename F |
| > |
| inline typename impl::make_composite< |
| OperationT, A, B, C, D, E, F |
| >::type |
| function<OperationT>::operator()( |
| A const& a, B const& b, C const& c, D const& d, E const& e, |
| F const& f |
| ) const |
| { |
| typedef typename impl::make_composite< |
| OperationT, A, B, C, D, E, F |
| >::composite_type ret_t; |
| |
| return ret_t( |
| op, |
| as_actor<A>::convert(a), |
| as_actor<B>::convert(b), |
| as_actor<C>::convert(c), |
| as_actor<D>::convert(d), |
| as_actor<E>::convert(e), |
| as_actor<F>::convert(f) |
| ); |
| } |
| |
| #if PHOENIX_LIMIT > 6 |
| |
| ////////////////////////////////// |
| template <typename OperationT> |
| template < |
| typename A, typename B, typename C, typename D, typename E, |
| typename F, typename G |
| > |
| inline typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G |
| >::type |
| function<OperationT>::operator()( |
| A const& a, B const& b, C const& c, D const& d, E const& e, |
| F const& f, G const& g |
| ) const |
| { |
| typedef typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G |
| >::composite_type ret_t; |
| |
| return ret_t( |
| op, |
| as_actor<A>::convert(a), |
| as_actor<B>::convert(b), |
| as_actor<C>::convert(c), |
| as_actor<D>::convert(d), |
| as_actor<E>::convert(e), |
| as_actor<F>::convert(f), |
| as_actor<G>::convert(g) |
| ); |
| } |
| |
| ////////////////////////////////// |
| template <typename OperationT> |
| template < |
| typename A, typename B, typename C, typename D, typename E, |
| typename F, typename G, typename H |
| > |
| inline typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H |
| >::type |
| function<OperationT>::operator()( |
| A const& a, B const& b, C const& c, D const& d, E const& e, |
| F const& f, G const& g, H const& h |
| ) const |
| { |
| typedef typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H |
| >::composite_type ret_t; |
| |
| return ret_t( |
| op, |
| as_actor<A>::convert(a), |
| as_actor<B>::convert(b), |
| as_actor<C>::convert(c), |
| as_actor<D>::convert(d), |
| as_actor<E>::convert(e), |
| as_actor<F>::convert(f), |
| as_actor<G>::convert(g), |
| as_actor<H>::convert(h) |
| ); |
| } |
| |
| ////////////////////////////////// |
| template <typename OperationT> |
| template < |
| typename A, typename B, typename C, typename D, typename E, |
| typename F, typename G, typename H, typename I |
| > |
| inline typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H, I |
| >::type |
| function<OperationT>::operator()( |
| A const& a, B const& b, C const& c, D const& d, E const& e, |
| F const& f, G const& g, H const& h, I const& i |
| ) const |
| { |
| typedef typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H, I |
| >::composite_type ret_t; |
| |
| return ret_t( |
| op, |
| as_actor<A>::convert(a), |
| as_actor<B>::convert(b), |
| as_actor<C>::convert(c), |
| as_actor<D>::convert(d), |
| as_actor<E>::convert(e), |
| as_actor<F>::convert(f), |
| as_actor<G>::convert(g), |
| as_actor<H>::convert(h), |
| as_actor<I>::convert(i) |
| ); |
| } |
| |
| #if PHOENIX_LIMIT > 9 |
| |
| ////////////////////////////////// |
| template <typename OperationT> |
| template < |
| typename A, typename B, typename C, typename D, typename E, |
| typename F, typename G, typename H, typename I, typename J |
| > |
| inline typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H, I, J |
| >::type |
| function<OperationT>::operator()( |
| A const& a, B const& b, C const& c, D const& d, E const& e, |
| F const& f, G const& g, H const& h, I const& i, J const& j |
| ) const |
| { |
| typedef typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H, I, J |
| >::composite_type ret_t; |
| |
| return ret_t( |
| op, |
| as_actor<A>::convert(a), |
| as_actor<B>::convert(b), |
| as_actor<C>::convert(c), |
| as_actor<D>::convert(d), |
| as_actor<E>::convert(e), |
| as_actor<F>::convert(f), |
| as_actor<G>::convert(g), |
| as_actor<H>::convert(h), |
| as_actor<I>::convert(i), |
| as_actor<J>::convert(j) |
| ); |
| } |
| |
| ////////////////////////////////// |
| template <typename OperationT> |
| template < |
| typename A, typename B, typename C, typename D, typename E, |
| typename F, typename G, typename H, typename I, typename J, |
| typename K |
| > |
| inline typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H, I, J, K |
| >::type |
| function<OperationT>::operator()( |
| A const& a, B const& b, C const& c, D const& d, E const& e, |
| F const& f, G const& g, H const& h, I const& i, J const& j, |
| K const& k |
| ) const |
| { |
| typedef typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H, I, J, K |
| >::composite_type ret_t; |
| |
| return ret_t( |
| op, |
| as_actor<A>::convert(a), |
| as_actor<B>::convert(b), |
| as_actor<C>::convert(c), |
| as_actor<D>::convert(d), |
| as_actor<E>::convert(e), |
| as_actor<F>::convert(f), |
| as_actor<G>::convert(g), |
| as_actor<H>::convert(h), |
| as_actor<I>::convert(i), |
| as_actor<J>::convert(j), |
| as_actor<K>::convert(k) |
| ); |
| } |
| |
| ////////////////////////////////// |
| template <typename OperationT> |
| template < |
| typename A, typename B, typename C, typename D, typename E, |
| typename F, typename G, typename H, typename I, typename J, |
| typename K, typename L |
| > |
| inline typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H, I, J, K, L |
| >::type |
| function<OperationT>::operator()( |
| A const& a, B const& b, C const& c, D const& d, E const& e, |
| F const& f, G const& g, H const& h, I const& i, J const& j, |
| K const& k, L const& l |
| ) const |
| { |
| typedef typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H, I, J, K, L |
| >::composite_type ret_t; |
| |
| return ret_t( |
| op, |
| as_actor<A>::convert(a), |
| as_actor<B>::convert(b), |
| as_actor<C>::convert(c), |
| as_actor<D>::convert(d), |
| as_actor<E>::convert(e), |
| as_actor<F>::convert(f), |
| as_actor<G>::convert(g), |
| as_actor<H>::convert(h), |
| as_actor<I>::convert(i), |
| as_actor<J>::convert(j), |
| as_actor<K>::convert(k), |
| as_actor<L>::convert(l) |
| ); |
| } |
| |
| #if PHOENIX_LIMIT > 12 |
| |
| ////////////////////////////////// |
| template <typename OperationT> |
| template < |
| typename A, typename B, typename C, typename D, typename E, |
| typename F, typename G, typename H, typename I, typename J, |
| typename K, typename L, typename M |
| > |
| inline typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H, I, J, K, L, M |
| >::type |
| function<OperationT>::operator()( |
| A const& a, B const& b, C const& c, D const& d, E const& e, |
| F const& f, G const& g, H const& h, I const& i, J const& j, |
| K const& k, L const& l, M const& m |
| ) const |
| { |
| typedef typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H, I, J, K, L, M |
| >::composite_type ret_t; |
| |
| return ret_t( |
| op, |
| as_actor<A>::convert(a), |
| as_actor<B>::convert(b), |
| as_actor<C>::convert(c), |
| as_actor<D>::convert(d), |
| as_actor<E>::convert(e), |
| as_actor<F>::convert(f), |
| as_actor<G>::convert(g), |
| as_actor<H>::convert(h), |
| as_actor<I>::convert(i), |
| as_actor<J>::convert(j), |
| as_actor<K>::convert(k), |
| as_actor<L>::convert(l), |
| as_actor<M>::convert(m) |
| ); |
| } |
| |
| ////////////////////////////////// |
| template <typename OperationT> |
| template < |
| typename A, typename B, typename C, typename D, typename E, |
| typename F, typename G, typename H, typename I, typename J, |
| typename K, typename L, typename M, typename N |
| > |
| inline typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H, I, J, K, L, M, N |
| >::type |
| function<OperationT>::operator()( |
| A const& a, B const& b, C const& c, D const& d, E const& e, |
| F const& f, G const& g, H const& h, I const& i, J const& j, |
| K const& k, L const& l, M const& m, N const& n |
| ) const |
| { |
| typedef typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H, I, J, K, L, M, N |
| >::composite_type ret_t; |
| |
| return ret_t( |
| op, |
| as_actor<A>::convert(a), |
| as_actor<B>::convert(b), |
| as_actor<C>::convert(c), |
| as_actor<D>::convert(d), |
| as_actor<E>::convert(e), |
| as_actor<F>::convert(f), |
| as_actor<G>::convert(g), |
| as_actor<H>::convert(h), |
| as_actor<I>::convert(i), |
| as_actor<J>::convert(j), |
| as_actor<K>::convert(k), |
| as_actor<L>::convert(l), |
| as_actor<M>::convert(m), |
| as_actor<N>::convert(n) |
| ); |
| } |
| |
| ////////////////////////////////// |
| template <typename OperationT> |
| template < |
| typename A, typename B, typename C, typename D, typename E, |
| typename F, typename G, typename H, typename I, typename J, |
| typename K, typename L, typename M, typename N, typename O |
| > |
| inline typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H, I, J, K, L, M, N, O |
| >::type |
| function<OperationT>::operator()( |
| A const& a, B const& b, C const& c, D const& d, E const& e, |
| F const& f, G const& g, H const& h, I const& i, J const& j, |
| K const& k, L const& l, M const& m, N const& n, O const& o |
| ) const |
| { |
| typedef typename impl::make_composite< |
| OperationT, A, B, C, D, E, F, G, H, I, J, K, L, M, N, O |
| >::composite_type ret_t; |
| |
| return ret_t( |
| op, |
| as_actor<A>::convert(a), |
| as_actor<B>::convert(b), |
| as_actor<C>::convert(c), |
| as_actor<D>::convert(d), |
| as_actor<E>::convert(e), |
| as_actor<F>::convert(f), |
| as_actor<G>::convert(g), |
| as_actor<H>::convert(h), |
| as_actor<I>::convert(i), |
| as_actor<J>::convert(j), |
| as_actor<K>::convert(k), |
| as_actor<L>::convert(l), |
| as_actor<M>::convert(m), |
| as_actor<N>::convert(n), |
| as_actor<O>::convert(o) |
| ); |
| } |
| |
| #endif |
| #endif |
| #endif |
| #endif |
| |
| /////////////////////////////////////////////////////////////////////////////// |
| } // namespace phoenix |
| |
| #endif |