00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012 #ifndef BOOST_DETAIL_NAMED_TEMPLATE_PARAMS_HPP
00013 #define BOOST_DETAIL_NAMED_TEMPLATE_PARAMS_HPP
00014
00015 #include <sysc/packages/boost/type_traits/conversion_traits.hpp>
00016 #include <sysc/packages/boost/type_traits/composite_traits.hpp>
00017 #if defined(__BORLANDC__)
00018 #include <sysc/packages/boost/type_traits/ice.hpp>
00019 #endif
00020
00021 namespace boost {
00022 namespace detail {
00023
00024 struct default_argument { };
00025
00026 struct dummy_default_gen {
00027 template <class Base, class Traits>
00028 struct select {
00029 typedef default_argument type;
00030 };
00031 };
00032
00033
00034 template <class Gen> struct default_generator {
00035 typedef detail::dummy_default_gen type;
00036 };
00037
00038 template <class T> struct is_default {
00039 enum { value = false };
00040 typedef type_traits::no_type type;
00041 };
00042 template <> struct is_default<default_argument> {
00043 enum { value = true };
00044 typedef type_traits::yes_type type;
00045 };
00046
00047 struct choose_default {
00048 template <class Arg, class DefaultGen, class Base, class Traits>
00049 struct select {
00050 typedef typename default_generator<DefaultGen>::type Gen;
00051 typedef typename Gen::template select<Base,Traits>::type type;
00052 };
00053 };
00054 struct choose_arg {
00055 template <class Arg, class DefaultGen, class Base, class Traits>
00056 struct select {
00057 typedef Arg type;
00058 };
00059 };
00060
00061 #if defined(__BORLANDC__)
00062 template <class UseDefault>
00063 struct choose_arg_or_default { typedef choose_arg type; };
00064 template <>
00065 struct choose_arg_or_default<type_traits::yes_type> {
00066 typedef choose_default type;
00067 };
00068 #else
00069 template <bool UseDefault>
00070 struct choose_arg_or_default { typedef choose_arg type; };
00071 template <>
00072 struct choose_arg_or_default<true> {
00073 typedef choose_default type;
00074 };
00075 #endif
00076
00077 template <class Arg, class DefaultGen, class Base, class Traits>
00078 class resolve_default {
00079 #if defined(__BORLANDC__)
00080 typedef typename choose_arg_or_default<typename is_default<Arg>::type>::type Selector;
00081 #else
00082
00083
00084 enum { is_def = is_default<Arg>::value };
00085 typedef typename choose_arg_or_default<is_def>::type Selector;
00086 #endif
00087 public:
00088 typedef typename Selector
00089 ::template select<Arg, DefaultGen, Base, Traits>::type type;
00090 };
00091
00092
00093
00094 struct named_template_param_base { };
00095
00096 template <class X>
00097 struct is_named_param_list {
00098 enum { value = is_convertible<X, named_template_param_base>::value };
00099 };
00100
00101 struct choose_named_params {
00102 template <class Prev> struct select { typedef Prev type; };
00103 };
00104 struct choose_default_arg {
00105 template <class Prev> struct select {
00106 typedef detail::default_argument type;
00107 };
00108 };
00109
00110 template <bool Named> struct choose_default_dispatch_;
00111 template <> struct choose_default_dispatch_<true> {
00112 typedef choose_named_params type;
00113 };
00114 template <> struct choose_default_dispatch_<false> {
00115 typedef choose_default_arg type;
00116 };
00117
00118 template <bool Named> struct choose_default_dispatch
00119 : public choose_default_dispatch_<Named> { };
00120
00121 template <class PreviousArg>
00122 struct choose_default_argument {
00123 enum { is_named = is_named_param_list<PreviousArg>::value };
00124 typedef typename choose_default_dispatch<is_named>::type Selector;
00125 typedef typename Selector::template select<PreviousArg>::type type;
00126 };
00127
00128
00129
00130
00131
00132
00133
00134
00135
00136
00137
00138
00139 #define BOOST_NAMED_TEMPLATE_PARAM(TYPE) \
00140 struct get_##TYPE##_from_named { \
00141 template <class Base, class NamedParams, class Traits> \
00142 struct select { \
00143 typedef typename NamedParams::traits NamedTraits; \
00144 typedef typename NamedTraits::TYPE TYPE; \
00145 typedef typename resolve_default<TYPE, \
00146 default_##TYPE, Base, NamedTraits>::type type; \
00147 }; \
00148 }; \
00149 struct pass_thru_##TYPE { \
00150 template <class Base, class Arg, class Traits> struct select { \
00151 typedef typename resolve_default<Arg, \
00152 default_##TYPE, Base, Traits>::type type; \
00153 };\
00154 }; \
00155 template <int NamedParam> \
00156 struct get_##TYPE##_dispatch { }; \
00157 template <> struct get_##TYPE##_dispatch<1> { \
00158 typedef get_##TYPE##_from_named type; \
00159 }; \
00160 template <> struct get_##TYPE##_dispatch<0> { \
00161 typedef pass_thru_##TYPE type; \
00162 }; \
00163 template <class Base, class X, class Traits> \
00164 class get_##TYPE { \
00165 enum { is_named = is_named_param_list<X>::value }; \
00166 typedef typename get_##TYPE##_dispatch<is_named>::type Selector; \
00167 public: \
00168 typedef typename Selector::template select<Base, X, Traits>::type type; \
00169 }; \
00170 template <> struct default_generator<default_##TYPE> { \
00171 typedef default_##TYPE type; \
00172 }
00173
00174
00175 }
00176 }
00177
00178 #endif // BOOST_DETAIL_NAMED_TEMPLATE_PARAMS_HPP