IMP  2.0.1
The Integrative Modeling Platform
tuple_macros.h
Go to the documentation of this file.
1 /**
2  * \file IMP/base/tuple_macros.h
3  * \brief Various general useful macros for IMP.
4  *
5  * Copyright 2007-2013 IMP Inventors. All rights reserved.
6  *
7  */
8 
9 #ifndef IMPBASE_TUPLE_MACROS_H
10 #define IMPBASE_TUPLE_MACROS_H
11 #include <IMP/base/base_config.h>
12 #include "Value.h"
13 #include "Showable.h"
14 #include "hash.h"
15 #include "hash_macros.h"
16 #include "showable_macros.h"
17 #include "value_macros.h"
18 #include "comparison_macros.h"
19 #include "swig_macros.h"
20 
21 /** Implementation macro */
22 #define IMP_TUPLE_VALUE(Name, type_name, data_name, var_name) \
23  private: \
24  type_name var_name; \
25 public: \
26  IMP_HELPER_MACRO_PUSH_WARNINGS \
27  const type_name &get_##data_name() const {return var_name;} \
28  void set_##data_name(const type_name &v) { \
29  var_name=v; \
30  } \
31  IMP_NO_SWIG(type_name& access_##data_name() {return var_name;})\
32  IMP_HELPER_MACRO_POP_WARNINGS
33 
34 
35 /** \name Named tuples
36  It is often useful to declare little structures to aid in the passing
37  of arguments by name or returning sets of values. One can use
38  boost::tuples, but these don't have names for their parts and so
39  don't lead to clear code. Instead we provide a macro to aid
40  declaring such classes. The resulting class is hashable and
41  comparable too.
42  @{
43 */
44 
45 #define IMP_NAMED_TUPLE_1(Name, Names, type0, var0, invariant) \
46  struct Name: public IMP::base::Value { \
47  Name(type0 i0=type0()): var0##_(i0){invariant;} \
48  IMP_HASHABLE_INLINE(Name, { \
49  std::size_t value= IMP::base::hash_value(var0##_); \
50  return value; \
51  }); \
52  IMP_COMPARISONS_1(Name); \
53  IMP_SHOWABLE_INLINE(Name, out << "(" << #var0 << "=" \
54  << IMP::base::Showable(var0##_) << ")"); \
55  IMP_TUPLE_VALUE(Name, type0, var0, var0##_); \
56  private: \
57  int compare(const Name &o) const { \
58  IMP_COMPARE_ONE(var0##_, o.var0##_); \
59  return 0; \
60  } \
61  }; \
62  IMP_VALUES(Name, Names)
63 
64 
65 
66 #define IMP_NAMED_TUPLE_2(Name, Names, type0, var0, type1, var1, \
67  invariant) \
68  struct Name: public IMP::base::Value { \
69  Name(type0 i0=type0(), type1 i1=type1()): var0##_(i0), var1##_(i1) \
70  {invariant;} \
71  IMP_HASHABLE_INLINE(Name, { \
72  std::size_t value= IMP::base::hash_value(var0##_); \
73  boost::hash_combine(value, IMP::base::hash_value(var1##_)); \
74  return value; \
75  }); \
76  IMP_SHOWABLE_INLINE(Name, out << "(" << #var0 << "=" \
77  << IMP::base::Showable(var0##_) \
78  << " " <<#var1 << "=" \
79  << IMP::base::Showable(var1##_) << ")"); \
80  IMP_COMPARISONS(Name); \
81  IMP_TUPLE_VALUE(Name, type0, var0, var0##_); \
82  IMP_TUPLE_VALUE(Name, type1, var1, var1##_); \
83  private: \
84  int compare(const Name &o) const { \
85  IMP_COMPARE_ONE(var0##_, o.var0##_); \
86  IMP_COMPARE_ONE(var1##_, o.var1##_); \
87  return 0; \
88  } \
89  }; \
90  IMP_VALUES(Name, Names)
91 
92 
93 #define IMP_NAMED_TUPLE_3(Name, Names, type0, var0, type1, var1, \
94  type2, var2, invariant) \
95  struct Name: public IMP::base::Value { \
96  Name(type0 i0=type0(), type1 i1=type1(),type2 i2=type2() \
97  ): var0##_(i0), var1##_(i1), var2##_(i2){invariant;} \
98  IMP_HASHABLE_INLINE(Name, { \
99  std::size_t value= IMP::base::hash_value(var0##_); \
100  boost::hash_combine(value, IMP::base::hash_value(var1##_)); \
101  boost::hash_combine(value, IMP::base::hash_value(var2##_)); \
102  return value; \
103  }); \
104  IMP_COMPARISONS(Name); \
105  IMP_SHOWABLE_INLINE(Name, out << "(" << #var0 << "=" \
106  << IMP::base::Showable(var0##_) \
107  << " " <<#var1 << "=" \
108  << IMP::base::Showable(var1##_) \
109  << " " <<#var2 << "=" \
110  << IMP::base::Showable(var2##_) << ")"); \
111  IMP_TUPLE_VALUE(Name, type0, var0, var0##_); \
112  IMP_TUPLE_VALUE(Name, type1, var1, var1##_); \
113  IMP_TUPLE_VALUE(Name, type2, var2, var2##_); \
114  private: \
115  int compare(const Name &o) const { \
116  IMP_COMPARE_ONE(var0##_, o.var0##_); \
117  IMP_COMPARE_ONE(var1##_, o.var1##_); \
118  IMP_COMPARE_ONE(var2##_, o.var2##_); \
119  return 0; \
120  } \
121  }; \
122  IMP_VALUES(Name, Names)
123 
124 
125 #define IMP_NAMED_TUPLE_4(Name, Names, type0, var0, type1, var1, \
126  type2, var2, type3, var3, invariant) \
127  struct Name: public IMP::base::Value { \
128  Name(type0 i0=type0(), type1 i1=type1(),type2 i2=type2(), \
129  type3 i3=type3()): var0##_(i0), var1##_(i1), var2##_(i2), \
130  var3##_(i3) {invariant;} \
131  IMP_HASHABLE_INLINE(Name, { \
132  std::size_t value= IMP::base::hash_value(var0##_); \
133  boost::hash_combine(value, IMP::base::hash_value(var1##_)); \
134  boost::hash_combine(value, IMP::base::hash_value(var2##_)); \
135  boost::hash_combine(value, IMP::base::hash_value(var3##_)); \
136  return value; \
137  }); \
138  IMP_COMPARISONS(Name); \
139  IMP_SHOWABLE_INLINE(Name, out << "(" << #var0 << "=" \
140  << IMP::base::Showable(var0##_) \
141  << " " <<#var1 << "=" \
142  << IMP::base::Showable(var1##_) \
143  << " " <<#var2 << "=" \
144  << IMP::base::Showable(var2##_) \
145  << " " <<#var3 << "=" \
146  << IMP::base::Showable(var3##_) \
147  << ")"); \
148  IMP_TUPLE_VALUE(Name, type0, var0, var0##_); \
149  IMP_TUPLE_VALUE(Name, type1, var1, var1##_); \
150  IMP_TUPLE_VALUE(Name, type2, var2, var2##_); \
151  IMP_TUPLE_VALUE(Name, type3, var3, var3##_); \
152  private: \
153  int compare(const Name &o) const { \
154  IMP_COMPARE_ONE(var0##_, o.var0##_); \
155  IMP_COMPARE_ONE(var1##_, o.var1##_); \
156  IMP_COMPARE_ONE(var2##_, o.var2##_); \
157  IMP_COMPARE_ONE(var3##_, o.var3##_); \
158  return 0; \
159  } \
160  }; \
161  IMP_VALUES(Name, Names)
162 
163 
164 #define IMP_NAMED_TUPLE_5(Name, Names, type0, var0, type1, var1, \
165  type2, var2, type3, var3, type4, var4, \
166  invariant) \
167  struct Name: public IMP::base::Value { \
168  Name(type0 i0=type0(), type1 i1=type1(),type2 i2=type2(), \
169  type3 i3=type3(), type4 i4=type4()): var0##_(i0), var1##_(i1), \
170  var2##_(i2), \
171  var3##_(i3), var4##_(i4) \
172  {invariant;} \
173  IMP_HASHABLE_INLINE(Name, { \
174  std::size_t value= IMP::base::hash_value(var0##_); \
175  boost::hash_combine(value, IMP::base::hash_value(var1##_)); \
176  boost::hash_combine(value, IMP::base::hash_value(var2##_)); \
177  boost::hash_combine(value, IMP::base::hash_value(var3##_)); \
178  boost::hash_combine(value, IMP::base::hash_value(var4##_)); \
179  return value; \
180  }); \
181  IMP_COMPARISONS(Name); \
182  IMP_SHOWABLE_INLINE(Name, out << "(" << #var0 << "=" \
183  << IMP::base::Showable(var0##_) \
184  << " " <<#var1 << "=" \
185  << IMP::base::Showable(var1##_) \
186  << " " <<#var2 << "=" \
187  << IMP::base::Showable(var2##_) \
188  << " " <<#var3 << "=" \
189  << IMP::base::Showable(var3##_) \
190  << " " <<#var4 << "=" \
191  << IMP::base::Showable(var4##_) \
192  << ")"); \
193  IMP_TUPLE_VALUE(Name, type0, var0, var0##_); \
194  IMP_TUPLE_VALUE(Name, type1, var1, var1##_); \
195  IMP_TUPLE_VALUE(Name, type2, var2, var2##_); \
196  IMP_TUPLE_VALUE(Name, type3, var3, var3##_); \
197  IMP_TUPLE_VALUE(Name, type4, var4, var4##_); \
198  private: \
199  int compare(const Name &o) const { \
200  IMP_COMPARE_ONE(var0##_, o.var0##_); \
201  IMP_COMPARE_ONE(var1##_, o.var1##_); \
202  IMP_COMPARE_ONE(var2##_, o.var2##_); \
203  IMP_COMPARE_ONE(var3##_, o.var3##_); \
204  IMP_COMPARE_ONE(var4##_, o.var4##_); \
205  return 0; \
206  } \
207  }; \
208  IMP_VALUES(Name, Names)
209 
210 
211 
212 /**@}*/
213 
214 #endif /* IMPBASE_TUPLE_MACROS_H */