• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*=============================================================================
2     Copyright (c) 2006-2007 Tobias Schwinger
3 
4     Use modification and distribution are subject to the Boost Software
5     License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
6     http://www.boost.org/LICENSE_1_0.txt).
7 ==============================================================================*/
8 
9 #if !defined(BOOST_FUSION_FUNCTIONAL_ADAPTER_UNFUSED_TYPED_HPP_INCLUDED)
10 #if !defined(BOOST_PP_IS_ITERATING)
11 
12 #include <boost/preprocessor/cat.hpp>
13 #include <boost/preprocessor/iteration/iterate.hpp>
14 #include <boost/preprocessor/repetition/enum.hpp>
15 #include <boost/preprocessor/repetition/enum_params.hpp>
16 #include <boost/preprocessor/repetition/enum_trailing_params.hpp>
17 
18 #include <boost/config.hpp>
19 
20 #include <boost/utility/result_of.hpp>
21 
22 #include <boost/fusion/support/detail/access.hpp>
23 #include <boost/fusion/sequence/intrinsic/value_at.hpp>
24 #include <boost/fusion/sequence/intrinsic/size.hpp>
25 #include <boost/fusion/container/vector/vector.hpp>
26 #include <boost/fusion/container/vector/convert.hpp>
27 
28 #include <boost/fusion/functional/adapter/limits.hpp>
29 #include <boost/fusion/functional/adapter/detail/access.hpp>
30 
31 #if defined (BOOST_MSVC)
32 #  pragma warning(push)
33 #  pragma warning (disable: 4512) // assignment operator could not be generated.
34 #endif
35 
36 
37 namespace boost { namespace fusion
38 {
39 
40     template <class Function, class Sequence> class unfused_typed;
41 
42     //----- ---- --- -- - -  -   -
43 
44     namespace detail
45     {
46         template <class Derived, class Function,
47             class Sequence, long Arity>
48         struct unfused_typed_impl;
49     }
50 
51     template <class Function, class Sequence>
52     class unfused_typed
53         : public detail::unfused_typed_impl
54           < unfused_typed<Function,Sequence>, Function, Sequence,
55             result_of::size<Sequence>::value >
56     {
57         Function fnc_transformed;
58 
59         template <class D, class F, class S, long A>
60         friend struct detail::unfused_typed_impl;
61 
62         typedef typename detail::call_param<Function>::type func_const_fwd_t;
63 
64     public:
65 
66         BOOST_CONSTEXPR BOOST_FUSION_GPU_ENABLED
unfused_typed(func_const_fwd_t f=Function ())67         inline explicit unfused_typed(func_const_fwd_t f = Function())
68             : fnc_transformed(f)
69         { }
70     };
71 
72     #define  BOOST_PP_FILENAME_1 <boost/fusion/functional/adapter/unfused_typed.hpp>
73     #define  BOOST_PP_ITERATION_LIMITS (0,BOOST_FUSION_UNFUSED_TYPED_MAX_ARITY)
74     #include BOOST_PP_ITERATE()
75 
76 }}
77 
78 #if defined (BOOST_MSVC)
79 #  pragma warning(pop)
80 #endif
81 
82 namespace boost
83 {
84 #if !defined(BOOST_RESULT_OF_USE_DECLTYPE) || defined(BOOST_NO_CXX11_DECLTYPE)
85     template<class F, class Seq>
86     struct result_of< boost::fusion::unfused_typed<F,Seq> const () >
87         : boost::fusion::unfused_typed<F,Seq>::template result<
88             boost::fusion::unfused_typed<F,Seq> const () >
89     { };
90     template<class F, class Seq>
91     struct result_of< boost::fusion::unfused_typed<F,Seq>() >
92         : boost::fusion::unfused_typed<F,Seq>::template result<
93             boost::fusion::unfused_typed<F,Seq> () >
94     { };
95 #endif
96     template<class F, class Seq>
97     struct tr1_result_of< boost::fusion::unfused_typed<F,Seq> const () >
98         : boost::fusion::unfused_typed<F,Seq>::template result<
99             boost::fusion::unfused_typed<F,Seq> const () >
100     { };
101     template<class F, class Seq>
102     struct tr1_result_of< boost::fusion::unfused_typed<F,Seq>() >
103         : boost::fusion::unfused_typed<F,Seq>::template result<
104             boost::fusion::unfused_typed<F,Seq> () >
105     { };
106 }
107 
108 
109 #define BOOST_FUSION_FUNCTIONAL_ADAPTER_UNFUSED_TYPED_HPP_INCLUDED
110 #else // defined(BOOST_PP_IS_ITERATING)
111 ///////////////////////////////////////////////////////////////////////////////
112 //
113 //  Preprocessor vertical repetition code
114 //
115 ///////////////////////////////////////////////////////////////////////////////
116 #define N BOOST_PP_ITERATION()
117 
118     namespace detail
119     {
120 
121         template <class Derived, class Function, class Sequence>
122         struct unfused_typed_impl<Derived,Function,Sequence,N>
123         {
124             typedef typename detail::qf_c<Function>::type function_c;
125             typedef typename detail::qf<Function>::type function;
126             typedef typename result_of::as_vector<Sequence>::type arg_vector_t;
127 
128         public:
129 
130 #define M(z,i,s)                                                                \
131     typename call_param<typename result_of::value_at_c<s,i>::type>::type a##i
132 
133             BOOST_CXX14_CONSTEXPR BOOST_FUSION_GPU_ENABLED
134             inline typename boost::result_of<
135                 function_c(arg_vector_t &) >::type
operator ()detail::unfused_typed_impl136             operator()(BOOST_PP_ENUM(N,M,arg_vector_t)) const
137             {
138 #if N > 0
139                 arg_vector_t arg(BOOST_PP_ENUM_PARAMS(N,a));
140 #else
141                 arg_vector_t arg;
142 #endif
143                 return static_cast<Derived const *>(this)->fnc_transformed(arg);
144             }
145 
146             BOOST_CXX14_CONSTEXPR BOOST_FUSION_GPU_ENABLED
147             inline typename boost::result_of<
148                 function(arg_vector_t &) >::type
operator ()detail::unfused_typed_impl149             operator()(BOOST_PP_ENUM(N,M,arg_vector_t))
150             {
151 #if N > 0
152                 arg_vector_t arg(BOOST_PP_ENUM_PARAMS(N,a));
153 #else
154                 arg_vector_t arg;
155 #endif
156                 return static_cast<Derived *>(this)->fnc_transformed(arg);
157             }
158 
159 #undef M
160 
161             template <typename Sig> struct result { typedef void type; };
162 
163             template <class Self BOOST_PP_ENUM_TRAILING_PARAMS(N,typename T)>
164             struct result< Self const (BOOST_PP_ENUM_PARAMS(N,T)) >
165                 : boost::result_of< function_c(arg_vector_t &) >
166             { };
167 
168             template <class Self BOOST_PP_ENUM_TRAILING_PARAMS(N,typename T)>
169             struct result< Self (BOOST_PP_ENUM_PARAMS(N,T)) >
170                 : boost::result_of< function(arg_vector_t &) >
171             { };
172         };
173 
174     } // namespace detail
175 
176 #undef N
177 #endif // defined(BOOST_PP_IS_ITERATING)
178 #endif
179 
180