CMS 3D CMS Logo

 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Pages
WrapperDetail.h
Go to the documentation of this file.
1 #ifndef DataFormats_Common_WrapperDetail_h
2 #define DataFormats_Common_WrapperDetail_h
3 
4 /*----------------------------------------------------------------------
5 
6 WrapperDetail: Metafunction support for compile-time selection of code.
7 
8 ----------------------------------------------------------------------*/
9 
10 #include <typeinfo>
11 namespace edm {
12 
13  //Need to specialize the case of std::vector<edm::Ptr<T>>
14  template<typename T> class Ptr;
15 
16  namespace detail {
17  typedef char (& no_tag)[1]; // type indicating FALSE
18  typedef char (& yes_tag)[2]; // type indicating TRUE
19 
20  // void swap_or_assign(T& a, T& b) will swap if T::swap(T&) is defined and assign otherwise
21  // Definitions for the following struct and function templates are not needed; we only require the declarations.
22  template<typename T, void (T::*)(T&)> struct swap_function;
23  template<typename T> static yes_tag has_swap(swap_function<T, &T::swap>* dummy);
24  template<typename T> static no_tag has_swap(...);
25 
26  template<typename T>
28  static bool const value = sizeof(has_swap<T>(0)) == sizeof(yes_tag);
29  };
30 
32  template<typename T> struct doSwapOrAssign<T, true> {
33  void operator()(T& thisProduct, T& otherProduct) {
34  thisProduct.swap(otherProduct);
35  }
36  };
37  template<typename T> struct doSwapOrAssign<T, false> {
38  void operator()(T& thisProduct, T& otherProduct) {
39  thisProduct = otherProduct;
40  }
41  };
42 
43 #ifndef __GCCXML__
44  // valueTypeInfo_() will return typeid(T::value_type) if T::value_type is declared and typeid(void) otherwise.
45  // Definitions for the following struct and function templates are not needed; we only require the declarations.
46  template<typename T> static yes_tag& has_value_type(typename T::value_type*);
47  template<typename T> static no_tag& has_value_type(...);
48 
49  template<typename T> struct has_typedef_value_type {
50  static const bool value = sizeof(has_value_type<T>(nullptr)) == sizeof(yes_tag);
51  };
53  template<typename T> struct getValueType<T, true> {
54  std::type_info const& operator()() {
55  return typeid(typename T::value_type);
56  }
57  };
58  template<typename T> struct getValueType<T, false> {
59  std::type_info const& operator()() {
60  return typeid(void);
61  }
62  };
63 
64  // memberTypeInfo_() will return typeid(T::member_type) if T::member_type is declared and typeid(void) otherwise.
65  // Definitions for the following struct and function templates are not needed; we only require the declarations.
66  template<typename T> static yes_tag& has_member_type(typename T::member_type*);
67  template<typename T> static no_tag& has_member_type(...);
68 
69  template<typename T> struct has_typedef_member_type {
70  static const bool value = sizeof(has_member_type<T>(nullptr)) == sizeof(yes_tag);
71  };
73  template<typename T> struct getMemberType<T, true> {
74  std::type_info const& operator()() {
75  return typeid(typename T::member_type);
76  }
77  };
78  template<typename T> struct getMemberType<T, false> {
79  std::type_info const& operator()() {
80  return typeid(void);
81  }
82  };
83 
84  template< typename T> struct has_typedef_member_type<std::vector<edm::Ptr<T> > > {
85  static const bool value = true;
86  };
87 
88  template <typename T> struct getMemberType<std::vector<edm::Ptr<T> >, true> {
89  std::type_info const& operator()() {
90  return typeid(T);
91  }
92  };
93 
94  // bool isMergeable_() will return true if T::mergeProduct(T const&) is declared and false otherwise
95  // bool mergeProduct_(WrapperBase const*) will merge products if T::mergeProduct(T const&) is defined
96  // Definitions for the following struct and function templates are not needed; we only require the declarations.
97  template<typename T, bool (T::*)(T const&)> struct mergeProduct_function;
98  template<typename T> static yes_tag has_mergeProduct(mergeProduct_function<T, &T::mergeProduct>* dummy);
99  template<typename T> static no_tag has_mergeProduct(...);
100 
101  template<typename T>
103  static bool const value =
104  sizeof(has_mergeProduct<T>(0)) == sizeof(yes_tag);
105  };
106 
108  template<typename T> struct getHasMergeFunction<T, true> {
109  bool operator()() {
110  return true;
111  }
112  };
113  template<typename T> struct getHasMergeFunction<T, false> {
114  bool operator()() {
115  return false;
116  }
117  };
119  template<typename T> struct doMergeProduct<T, true> {
120  bool operator()(T& thisProduct, T const& newProduct) {
121  return thisProduct.mergeProduct(newProduct);
122  }
123  };
124  template<typename T> struct doMergeProduct<T, false> {
125  bool operator()(T& thisProduct, T const& newProduct) {
126  return true; // Should never be called
127  }
128  };
129 
130  // bool hasIsProductEqual_() will return true if T::isProductEqual(T const&) const is declared and false otherwise
131  // bool isProductEqual _(WrapperBase const*) will call T::isProductEqual(T const&) if it is defined
132  // Definitions for the following struct and function templates are not needed; we only require the declarations.
133  template<typename T, bool (T::*)(T const&) const> struct isProductEqual_function;
135  template<typename T> static no_tag has_isProductEqual(...);
136 
137  template<typename T>
139  static bool const value =
140  sizeof(has_isProductEqual<T>(0)) == sizeof(yes_tag);
141  };
142 
144  template<typename T> struct getHasIsProductEqual<T, true> {
145  bool operator()() {
146  return true;
147  }
148  };
149  template<typename T> struct getHasIsProductEqual<T, false> {
150  bool operator()() {
151  return false;
152  }
153  };
155  template<typename T> struct doIsProductEqual<T, true> {
156  bool operator()(T const& thisProduct, T const& newProduct) {
157  return thisProduct.isProductEqual(newProduct);
158  }
159  };
160  template<typename T> struct doIsProductEqual<T, false> {
161  bool operator()(T const& thisProduct, T const& newProduct) {
162  return true; // Should never be called
163  }
164  };
165 #endif
166  }
167 }
168 #endif
char(& yes_tag)[2]
Definition: WrapperDetail.h:18
std::type_info const & operator()()
Definition: WrapperDetail.h:79
std::type_info const & operator()()
Definition: WrapperDetail.h:59
static yes_tag has_isProductEqual(isProductEqual_function< T,&T::isProductEqual > *dummy)
static yes_tag has_mergeProduct(mergeProduct_function< T,&T::mergeProduct > *dummy)
bool operator()(T const &thisProduct, T const &newProduct)
bool operator()(T &thisProduct, T const &newProduct)
std::type_info const & operator()()
Definition: WrapperDetail.h:74
Container::value_type value_type
char(& no_tag)[1]
Definition: WrapperDetail.h:17
static yes_tag & has_member_type(typename T::member_type *)
bool operator()(T const &thisProduct, T const &newProduct)
std::type_info const & operator()()
Definition: WrapperDetail.h:54
void operator()(T &thisProduct, T &otherProduct)
Definition: WrapperDetail.h:38
static yes_tag & has_value_type(typename T::value_type *)
volatile std::atomic< bool > shutdown_flag false
long double T
void operator()(T &thisProduct, T &otherProduct)
Definition: WrapperDetail.h:33
bool operator()(T &thisProduct, T const &newProduct)
static yes_tag has_swap(swap_function< T,&T::swap > *dummy)