IMP  2.0.1
The Integrative Modeling Platform
grid_indexes.h
Go to the documentation of this file.
1 /**
2  * \file IMP/algebra/grid_indexes.h \brief A class to represent a voxel grid.
3  *
4  * Copyright 2007-2013 IMP Inventors. All rights reserved.
5  *
6  */
7 
8 #ifndef IMPALGEBRA_GRID_INDEXES_H
9 #define IMPALGEBRA_GRID_INDEXES_H
10 
11 #include <IMP/algebra/algebra_config.h>
13 #include "internal/vector.h"
14 #include "internal/grid_internal.h"
15 #include <IMP/base/types.h>
16 #include <IMP/base/Value.h>
17 #include <IMP/base/exception.h>
18 
19 IMPALGEBRA_BEGIN_NAMESPACE
20 
21 //! An index in an infinite grid on space
22 /* The index entries can be positive or negative and do not need to correspond
23  directly to cells in the grid. They get mapped on to actual grid cells
24  by various functions.
25  \see Grid3D
26 */
27 template < int D>
29  internal::VectorData<int, D, true> data_;
30  int compare(const ExtendedGridIndexD<D> &o) const {
31  if (D==-1) {
32  if (data_.get_dimension()==0 && o.data_.get_dimension()==0) {
33  return 0;
34  } else if (data_.get_dimension()==0) {
35  return -1;
36  } else if (o.data_.get_dimension()==0) {
37  return 1;
38  }
39  } else {
40  IMP_USAGE_CHECK(get_dimension() == o.get_dimension(),
41  "Dimensions don't match");
42  }
43  return internal::lexicographical_compare(begin(), end(),
44  o.begin(), o.end());
45  }
46  public:
47 #if !defined(IMP_DOXYGEN) && !defined(SWIG)
48  const internal::VectorData<int, D, true>& get_data() const {
49  return data_;
50  }
51  internal::VectorData<int, D, true>& access_data() {
52  return data_;
53  }
54 #endif
55  //! Create a grid cell from three arbitrary indexes
56  explicit ExtendedGridIndexD(Ints vals) {
57  data_.set_coordinates(vals.begin(), vals.end());
58  }
59 #ifndef SWIG
60  template <class It>
61  ExtendedGridIndexD(It b, It e) {
62  data_.set_coordinates(b,e);
63  }
64 #endif
65  ExtendedGridIndexD(int x, int y, int z) {
66  IMP_USAGE_CHECK(D==3, "Can only use explicit constructor in 3D");
67  int v[]={x,y,z};
68  data_.set_coordinates(v, v+3);
69  }
70  ExtendedGridIndexD() {
71  }
72  unsigned int get_dimension() const {
73  return data_.get_dimension();
74  }
75  IMP_COMPARISONS(ExtendedGridIndexD);
76  //! Get the ith component (i=0,1,2)
77  IMP_BRACKET(int, unsigned int,
78  i <get_dimension(),
79  IMP_USAGE_CHECK(!data_.get_is_null(),
80  "Using uninitialized grid index");
81  return data_.get_data()[i]);
82  IMP_SHOWABLE_INLINE(ExtendedGridIndexD, {
83  out << "(";
84  for (unsigned int i=0; i< get_dimension(); ++i) {
85  out<< operator[](i);
86  if (i != get_dimension()-1) out << ", ";
87  }
88  out << ")";
89  });
90 
91 #ifndef SWIG
92  typedef const int* iterator;
93  iterator begin() const {return data_.get_data();}
94  iterator end() const {return data_.get_data()+get_dimension();}
95 #endif
96 #ifndef IMP_DOXYGEN
97  unsigned int __len__() const { return get_dimension();}
98 #endif
99  IMP_HASHABLE_INLINE(ExtendedGridIndexD,
100  return boost::hash_range(begin(), end()));
101  ExtendedGridIndexD<D> get_uniform_offset(int ii) const {
102  Ints ret(get_dimension(), 0);
103  for (unsigned int i=0; i< get_dimension(); ++i) {
104  ret[i]= operator[](i)+ii;
105  }
106  //std::cout << "Offset " << *this << " to get " << ret << std::endl;
107  return ExtendedGridIndexD<D>(ret);
108  }
109  ExtendedGridIndexD<D> get_offset(int i, int j, int k) const {
110  IMP_USAGE_CHECK(D==3, "Only for 3D");
111  int v[]={operator[](0)+i,
112  operator[](1)+j,
113  operator[](2)+k};
114  ExtendedGridIndexD<D> ret(v, v+3);
115  return ret;
116  }
117 };
118 
119 #if !defined(SWIG) && !defined(IMP_DOXYGEN)
120 template < int D>
121 inline std::size_t hash_value(const ExtendedGridIndexD<D> &ind) {
122  return ind.__hash__();
123 }
124 #endif
125 
126 
127 
128 
129 
130 
131 
132 
133 
134 
135 
136 //! Represent a real cell in a grid (one within the bounding box)
137 /* These indexes represent an actual cell in the grid.
138  They can only be constructed by the grid (since only it knows what
139  are the actual cells).
140  \see Grid3D
141 */
142 template <int D>
143 class GridIndexD: public base::Value
144 {
145  internal::VectorData<int, D, true> data_;
146  int compare(const GridIndexD<D> &o) const {
147  if (D==-1) {
148  if (data_.get_dimension()==0 && o.data_.get_dimension()==0) {
149  return 0;
150  } else if (data_.get_dimension()==0) {
151  return -1;
152  } else if (o.data_.get_dimension()==0) {
153  return 1;
154  }
155  } else {
156  IMP_USAGE_CHECK(get_dimension() == o.get_dimension(),
157  "Dimensions don't match");
158  }
159  return internal::lexicographical_compare(begin(), end(),
160  o.begin(), o.end());
161  }
162  public:
163 #if !defined(IMP_DOXYGEN) && !defined(SWIG)
164  const internal::VectorData<int, D, true>& get_data() const {
165  return data_;
166  }
167  internal::VectorData<int, D, true>& access_data() {
168  return data_;
169  }
170 #endif
171  GridIndexD() {
172  }
173 
174  unsigned int get_dimension() const {return data_.get_dimension();}
175 
176 #ifndef IMP_DOXYGEN
177  //! Get the ith component (i=0,1,2)
178  IMP_CONST_BRACKET(int, unsigned int,
179  i < get_dimension(),
180  IMP_USAGE_CHECK(!data_.get_is_null(),
181  "Using uninitialized grid index");
182  return data_.get_data()[i]);
184  out << "(";
185  for (unsigned int i=0; i< get_dimension(); ++i) {
186  out<< operator[](i);
187  if (i != get_dimension()-1) out << ", ";
188  }
189  out << ")";
190  });
191 #ifndef SWIG
192  typedef const int* iterator;
193  iterator begin() const {return data_.get_data();}
194  iterator end() const {return data_.get_data()+get_dimension();}
195  explicit GridIndexD(Ints vals) {
196  data_.set_coordinates(vals.begin(), vals.end());
197  }
198  template <class It>
199  GridIndexD(It b, It e) {
200  data_.set_coordinates(b,e);
201  }
202 #endif
203  unsigned int __len__() const { return get_dimension();}
204 #endif
207  return boost::hash_range(begin(), end()));
208 };
209 
210 
211 #if !defined(SWIG) && !defined(IMP_DOXYGEN)
212 template < int D>
213 inline std::size_t hash_value(const GridIndexD<D> &ind) {
214  return ind.__hash__();
215 }
216 #endif
217 
218 
219 
220 
221 
222 
223 
224 #if !defined(IMP_DOXYGEN)
225 typedef GridIndexD<1> GridIndex1D;
226 typedef ExtendedGridIndexD<1> ExtendedGridIndex1D;
227 typedef base::Vector<GridIndex1D> GridIndex1Ds;
228 typedef base::Vector<ExtendedGridIndex1D> ExtendedGridIndex1Ds;
229 
230 
231 typedef GridIndexD<2> GridIndex2D;
232 typedef ExtendedGridIndexD<2> ExtendedGridIndex2D;
233 typedef base::Vector<GridIndex2D> GridIndex2Ds;
235 ExtendedGridIndex2Ds;
236 
237 typedef GridIndexD<3> GridIndex3D;
238 typedef ExtendedGridIndexD<3> ExtendedGridIndex3D;
239 typedef base::Vector<GridIndex3D> GridIndex3Ds;
241 ExtendedGridIndex3Ds;
242 
243 typedef GridIndexD<4> GridIndex4D;
244 typedef ExtendedGridIndexD<4> ExtendedGridIndex4D;
245 typedef base::Vector<GridIndex4D> GridIndex4Ds;
247 ExtendedGridIndex4Ds;
248 
249 typedef GridIndexD<5> GridIndex5D;
250 typedef ExtendedGridIndexD<5> ExtendedGridIndex5D;
251 typedef base::Vector<GridIndex5D> GridIndex5Ds;
253 ExtendedGridIndex5Ds;
254 
255 typedef GridIndexD<6> GridIndex6D;
256 typedef ExtendedGridIndexD<6> ExtendedGridIndex6D;
257 typedef base::Vector<GridIndex6D> GridIndex6Ds;
259 ExtendedGridIndex6Ds;
260 
261 typedef GridIndexD<-1> GridIndexKD;
262 typedef ExtendedGridIndexD<-1> ExtendedGridIndexKD;
263 typedef base::Vector<GridIndexKD> GridIndexKDs;
265 ExtendedGridIndexKDs;
266 #endif
267 
268 IMPALGEBRA_END_NAMESPACE
269 
270 
271 #endif /* IMPALGEBRA_GRID_INDEXES_H */