1// Copyright David Abrahams 2006. Distributed under the Boost
2// Software License, Version 1.0. (See accompanying
3// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
4//
5// #include guards intentionally disabled.
6// #ifndef BOOST_DETAIL_FUNCTION_N_DWA2006514_HPP
7// # define BOOST_DETAIL_FUNCTION_N_DWA2006514_HPP
8
9#include <boost/mpl/void.hpp>
10#include <boost/mpl/apply.hpp>
11
12#include <boost/preprocessor/control/if.hpp>
13#include <boost/preprocessor/cat.hpp>
14#include <boost/preprocessor/punctuation/comma_if.hpp>
15#include <boost/preprocessor/repetition/enum_params.hpp>
16#include <boost/preprocessor/repetition/enum_trailing_params.hpp>
17#include <boost/preprocessor/repetition/repeat.hpp>
18#include <boost/preprocessor/seq/fold_left.hpp>
19#include <boost/preprocessor/seq/seq.hpp>
20#include <boost/preprocessor/seq/for_each.hpp>
21#include <boost/preprocessor/seq/for_each_i.hpp>
22#include <boost/preprocessor/seq/for_each_product.hpp>
23#include <boost/preprocessor/seq/size.hpp>
24#include <boost/type_traits/add_const.hpp>
25#include <boost/type_traits/remove_reference.hpp>
26
27namespace boost { namespace detail {
28
29# define BOOST_DETAIL_default_arg(z, n, _) \
30 typedef mpl::void_ BOOST_PP_CAT(arg, n);
31
32# define BOOST_DETAIL_function_arg(z, n, _) \
33 typedef typename remove_reference< \
34 typename add_const< BOOST_PP_CAT(A, n) >::type \
35 >::type BOOST_PP_CAT(arg, n);
36
37#define BOOST_DETAIL_cat_arg_counts(s, state, n) \
38 BOOST_PP_IF( \
39 n \
40 , BOOST_PP_CAT(state, BOOST_PP_CAT(_, n)) \
41 , state \
42 ) \
43 /**/
44
45#define function_name \
46 BOOST_PP_SEQ_FOLD_LEFT( \
47 BOOST_DETAIL_cat_arg_counts \
48 , BOOST_PP_CAT(function, BOOST_PP_SEQ_HEAD(args)) \
49 , BOOST_PP_SEQ_TAIL(args)(0) \
50 ) \
51 /**/
52
53template<typename F>
54struct function_name
55{
56 BOOST_PP_REPEAT(
57 BOOST_MPL_LIMIT_METAFUNCTION_ARITY
58 , BOOST_DETAIL_default_arg
59 , ~
60 )
61
62 template<typename Signature>
63 struct result {};
64
65#define BOOST_DETAIL_function_result(r, _, n) \
66 template<typename This BOOST_PP_ENUM_TRAILING_PARAMS(n, typename A)> \
67 struct result<This(BOOST_PP_ENUM_PARAMS(n, A))> \
68 { \
69 BOOST_PP_REPEAT(n, BOOST_DETAIL_function_arg, ~) \
70 typedef \
71 typename BOOST_PP_CAT(mpl::apply, BOOST_MPL_LIMIT_METAFUNCTION_ARITY)<\
72 F \
73 BOOST_PP_ENUM_TRAILING_PARAMS( \
74 BOOST_MPL_LIMIT_METAFUNCTION_ARITY \
75 , arg \
76 ) \
77 >::type \
78 impl; \
79 typedef typename impl::result_type type; \
80 }; \
81 /**/
82
83 BOOST_PP_SEQ_FOR_EACH(BOOST_DETAIL_function_result, _, args)
84
85# define arg_type(r, _, i, is_const) \
86 BOOST_PP_COMMA_IF(i) BOOST_PP_CAT(A, i) BOOST_PP_CAT(const_if, is_const) &
87
88# define result_(r, n, constness) \
89 typename result< \
90 function_name( \
91 BOOST_PP_SEQ_FOR_EACH_I_R(r, arg_type, ~, constness) \
92 ) \
93 > \
94 /**/
95
96# define param(r, _, i, is_const) BOOST_PP_COMMA_IF(i) \
97 BOOST_PP_CAT(A, i) BOOST_PP_CAT(const_if, is_const) & BOOST_PP_CAT(x, i)
98
99# define param_list(r, n, constness) \
100 BOOST_PP_SEQ_FOR_EACH_I_R(r, param, ~, constness)
101
102# define call_operator(r, constness) \
103 template<BOOST_PP_ENUM_PARAMS(BOOST_PP_SEQ_SIZE(constness), typename A)> \
104 result_(r, BOOST_PP_SEQ_SIZE(constness), constness)::type \
105 operator ()( param_list(r, BOOST_PP_SEQ_SIZE(constness), constness) ) const \
106 { \
107 typedef result_(r, BOOST_PP_SEQ_SIZE(constness), constness)::impl impl; \
108 return impl()(BOOST_PP_ENUM_PARAMS(BOOST_PP_SEQ_SIZE(constness), x)); \
109 } \
110 /**/
111
112# define const_if0
113# define const_if1 const
114
115# define bits(z, n, _) ((0)(1))
116
117# define gen_operator(r, _, n) \
118 BOOST_PP_SEQ_FOR_EACH_PRODUCT_R( \
119 r \
120 , call_operator \
121 , BOOST_PP_REPEAT(n, bits, ~) \
122 ) \
123 /**/
124
125 BOOST_PP_SEQ_FOR_EACH(
126 gen_operator
127 , ~
128 , args
129 )
130
131# undef bits
132# undef const_if1
133# undef const_if0
134# undef call_operator
135# undef param_list
136# undef param
137# undef result_
138# undef default_
139# undef arg_type
140# undef gen_operator
141# undef function_name
142
143# undef args
144};
145
146}} // namespace boost::detail
147
148//#endif // BOOST_DETAIL_FUNCTION_N_DWA2006514_HPP
149

source code of include/boost/accumulators/numeric/detail/function_n.hpp