nav.hpp
Go to the documentation of this file.
1 #ifndef OPM_VERTEQ_NAV_HPP_INCLUDED
2 #define OPM_VERTEQ_NAV_HPP_INCLUDED
3 
4 // Copyright (C) 2013 Uni Research AS
5 // This file is licensed under the GNU General Public License v3.0
6 
7 #ifndef OPM_GRID_HEADER_INCLUDED
8 #include <opm/core/grid.h>
9 #endif
10 
11 #include <cstdlib> // div_t
12 #include <iosfwd> // ostream
13 
53 struct Coord2D {
54  Coord2D (int i_, int j_) : m_i (i_), m_j (j_) { }
55 
56  int i() const { return m_i; }
57  int j() const { return m_j; }
58 
62  bool operator == (const Coord2D& rhs) const {
63  return (m_i == rhs.m_i) && (m_j == rhs.m_j);
64  }
65 
66 protected:
67  const int m_i;
68  const int m_j;
69 
70  friend std::ostream& operator << (std::ostream& s, const Coord2D& c);
71 };
72 
74 struct Coord3D : public Coord2D {
75  Coord3D (int i_, int j_, int k_)
76  : Coord2D (i_, j_)
77  , m_k (k_) {
78  }
79 
80  int k() const { return m_k; }
81 
82 protected:
83  const int m_k;
84 
85  friend std::ostream& operator << (std::ostream& s, const Coord3D& c);
86 };
87 
88 // forward declaration
89 template <typename Dim > struct Side;
90 
92 struct Dir {
94  static const Dir DEC; // = 0
95 
97  static const Dir INC; // = 1
98 
100  static const int COUNT = 2;
101 
103  const int val;
104 
105  Dir (const Dir& rhs) : val (rhs.val) {}
106  bool operator == (const Dir& rhs) const { return val == rhs.val; }
107 
109  Dir opposite () const { return Dir (-(val - 1)); }
110 
111 protected:
113  Dir (int i) : val (i) { }
114 
115  template <typename Dim> friend struct Side;
116 
117  friend std::ostream& operator << (std::ostream& os, const Dir& d);
118 };
119 
120 struct Dim1D {
121  static const int COUNT = 1;
122 };
123 
125 struct Dim2D : public Dim1D {
126  // two spatial directions
127  static const Dim2D X; // = 0
128  static const Dim2D Y; // = 1
129 
130  // number of dimensions
131  static const int COUNT = 2;
132 
133  const int val;
134 
135  Dim2D (const Dim2D& rhs) : val (rhs.val) { }
136  bool operator == (const Dim2D& rhs) const { return val == rhs.val; }
137 
139  Dim2D orthogonal () const { return Dim2D (-(val - 1)); }
140 
141 protected:
142  Dim2D (int i) : val (i) { }
143 
144  friend struct Side <Dim2D>;
145 
146  friend std::ostream& operator << (std::ostream& os, const Dim2D& d);
147 };
148 
150 struct Dim3D : public Dim2D {
151  // added dimension in 3D
152  static const Dim3D Z; // = 2
153 
154  // number of dimensions (shadows Dim2D)
155  static const int COUNT = 3;
156 
157  Dim3D (const Dim3D& rhs) : Dim2D (rhs.val) { }
158  bool operator == (const Dim2D& rhs) const { return val == rhs.val; }
159 
160  // allow X and Y to work in 3D too
161  Dim3D (const Dim2D& rhs) : Dim2D (rhs) {}
162 
163 protected:
164  Dim3D (int i) : Dim2D (i) { }
165 
166  friend struct Side <Dim3D>;
167 };
168 
175 template <typename Dim>
176 struct Side {
177  Side (Dim dim_, Dir dir_) : m_dim (dim_), m_dir (dir_) { }
178  Side (const Side& rhs) : m_dim (rhs.m_dim), m_dir (rhs.m_dir) { }
179 
187  int facetag () const {
188  return dim().val * Dir::COUNT + dir().val;
189  }
190 
194  static Side <Dim> from_tag (int tag);
195 
196  Dim dim() const { return m_dim; }
197  Dir dir() const { return m_dir; }
198 
202  static const int COUNT = Dim::COUNT * Dir::COUNT;
203 
207  static const Side* begin () { return &ALL[0]; }
208  static const Side* end () { return &ALL[COUNT]; }
209 
213  bool operator == (const Side <Dim>& rhs) const {
214  return (m_dim == rhs.m_dim) && (m_dir == rhs.m_dir);
215  }
216 
217 protected:
218  const Dim m_dim;
219  const Dir m_dir;
220 
221  // fixed enumeration of all sides
222  static const Side ALL [];
223 
224  template <typename T>
225  friend std::ostream& operator << (std::ostream& os, const Side<T>& s);
226 };
227 
228 // specializations for the dimensions we work with
231 
232 // forward declaration of stream operator present in library
233 std::ostream& operator << (std::ostream& os, const Side2D& s);
234 std::ostream& operator << (std::ostream& os, const Side3D& s);
235 
236 // standalone constants for sides that we use; we call them 'up' and
237 // 'down' so that U and D are mnemonics, in contrast to 'top' and 'bottom'
238 // where the 'b' would conflict with 'back'.
239 extern const Side3D UP;
240 extern const Side3D DOWN;
241 
246 struct Corn2D {
247  Corn2D (Dir i_, Dir j_) : m_i (i_), m_j (j_) { }
248  Corn2D (const Corn2D& rhs) : m_i (rhs.m_i), m_j (rhs.m_j) { }
249 
250  Dir i() const { return m_i; }
251  Dir j() const { return m_j; }
252 
253 protected:
254  const Dir m_i;
255  const Dir m_j;
256 };
257 
262 struct Corn3D : public Corn2D {
263  Corn3D (Dir i_, Dir j_, Dir k_) : Corn2D (i_, j_), m_k (k_) { }
264  Corn3D (const Corn3D& rhs) : Corn2D (rhs), m_k (rhs.m_k) { }
265 
274  Corn3D pivot (Dim3D dim, Dir dir) {
275  return Corn3D (dim == Dim3D::X ? dir : m_i,
276  dim == Dim3D::Y ? dir : m_j,
277  dim == Dim3D::Z ? dir : m_k);
278  }
279 
280  Dir k() const { return m_k; }
281 
285  bool operator == (const Corn3D& rhs) const {
286  return (m_i == rhs.m_i) && (m_j == rhs.m_j) && (m_k == rhs.m_k);
287  }
288 
289 protected:
290  const Dir m_k;
291 
292  friend std::ostream& operator << (std::ostream& os, const Corn3D& c);
293 };
294 
299 struct Cart2D {
300  // number of cells in each direction
301  const int ni;
302  const int nj;
303 
304  // initialize from the size of the grid
305  Cart2D (int ni_, int nj_) : ni (ni_), nj (nj_) { }
306 
307  // use these two value types for structured coordinates and
308  // flattened indices, respectively
309  typedef Coord2D coord_t;
310  typedef int elem_t;
311  typedef int node_t;
312  typedef int face_t;
313 
315  static const int NO_ELEM; // = -1
316  static const int NO_FACE; // = -1
317  static const int NO_NODE; // = -1
318 
320  int num_elems () const {
321  return ni * nj;
322  }
323 
325  elem_t cart_ndx (const coord_t& coord) const {
326  return coord.j() * ni + coord.i();
327  }
328 
330  coord_t coord (const elem_t& cart_ndx) const {
331  const std::div_t strip = std::div (cart_ndx, ni);
332  const int i = strip.rem;
333  const int j = strip.quot;
334  return coord_t (i, j);
335  }
336 
341  int num_nodes () const {
342  return (ni + 1) * (nj + 1);
343  }
344 
345  node_t node_ndx (const coord_t& coord, const Corn2D& corn) {
346  return (coord.j() + corn.j().val) * (ni + 1) + (coord.i() + corn.i().val);
347  }
348 
353  int num_faces () const {
354  // there are ni+1 faces oriented in j-direction in each column,
355  // for a total of (ni+1)*nj, and nj+1 faces in i-direction in
356  // each row, for a total of (nj+1)*ni.
357  return (ni + 1) * nj + ni * (nj + 1);
358  }
359 
364  face_t face_ndx (const coord_t& coord, const Side2D& side) {
365  // flags that code 1 (include) or 0 (don't) for each of the tests
366  const int dirv = side.dir().val;
367  const int idim = side.dim() == Dim2D::X ? 1 : 0;
368  const int idir = idim ? dirv : 0;
369  const int jdir = idim ? 0 : dirv;
370  // there is a left side and a lower side face for each element in a
371  // column, plus one face at the top of each column; 2*ni+1. the j-
372  // coordinate plus one extra if we are selecting the right face, tells
373  // us which column which is to the left of or "above" the face.
374  // if the side is in the i-direction to the center of the element, then
375  // the face is aligned with the j axis, so we skip idim*ni i-aligned
376  // faces before it.
377  // finally, determine the row by using the i-coordinate, and i-direction
378  // to determine whether it is the lower or upper face (if applicable).
379  return (coord.j() + jdir) * (2 * ni + 1) + (idim * ni) + (coord.i() + idir);
380  }
381 };
382 
391 struct Cart3D {
392  // number of cells in each direction
393  const int ni;
394  const int nj;
395  const int nk;
396 
398  Cart3D (const UnstructuredGrid& g)
399  : ni (g.cartdims [0])
400  , nj (g.cartdims [1])
401  , nk (g.cartdims [2]) { }
402 
404  Cart2D project () const {
405  return Cart2D (ni, nj);
406  }
407 
408  // use these two value types for structured coordinates and
409  // flattened indices, respectively
410  typedef Coord3D coord_t;
411  typedef int elem_t;
412 
414  coord_t coord (const elem_t& cart_ndx) const {
415  // the i-index moves fastest, as this is Fortran-indexing
416  const div_t strip = div (cart_ndx, ni);
417  const int i = strip.rem;
418  const div_t plane = div (strip.quot, nj);
419  const int j = plane.rem;
420  const int k = plane.quot;
421  return coord_t (i, j, k);
422  }
423 };
424 
425 #endif // OPM_VERTEQ_NAV_HPP_INCLUDED
int j() const
Definition: nav.hpp:57
Definition: nav.hpp:262
Coord2D(int i_, int j_)
Definition: nav.hpp:54
static const int COUNT
Number of possible directions.
Definition: nav.hpp:100
const int m_i
Definition: nav.hpp:67
bool operator==(const Dim2D &rhs) const
Definition: nav.hpp:136
Side(const Side &rhs)
Definition: nav.hpp:178
const Dir m_i
Definition: nav.hpp:254
Corn2D(const Corn2D &rhs)
Definition: nav.hpp:248
static const int COUNT
Definition: nav.hpp:155
const int m_k
Definition: nav.hpp:83
static const Dim3D Z
Definition: nav.hpp:152
const Dir m_j
Definition: nav.hpp:255
Dim2D orthogonal() const
Orthogonal dimension to this one.
Definition: nav.hpp:139
Dim2D(int i)
Definition: nav.hpp:142
static const int NO_ELEM
Value used to indicate that a reference is not to a valid element.
Definition: nav.hpp:315
Dir opposite() const
Opposite direction to this one.
Definition: nav.hpp:109
int facetag() const
Definition: nav.hpp:187
const int val
Definition: nav.hpp:133
Side(Dim dim_, Dir dir_)
Definition: nav.hpp:177
static const int COUNT
Definition: nav.hpp:202
Dim2D(const Dim2D &rhs)
Definition: nav.hpp:135
Type-safe enumeration of axis dimensions in 3D.
Definition: nav.hpp:150
bool operator==(const Dim2D &rhs) const
Definition: nav.hpp:158
Type-safe enumeration of axis dimensions.
Definition: nav.hpp:125
static const Dim2D X
Definition: nav.hpp:127
Corn3D(Dir i_, Dir j_, Dir k_)
Definition: nav.hpp:263
const int nk
Definition: nav.hpp:395
static const int COUNT
Definition: nav.hpp:131
const int nj
Definition: nav.hpp:394
static Side< Dim > from_tag(int tag)
int num_faces() const
Definition: nav.hpp:353
const Dir m_k
Definition: nav.hpp:290
Cart2D project() const
Project grid into a surface.
Definition: nav.hpp:404
Definition: nav.hpp:299
Dir j() const
Definition: nav.hpp:251
Dir dir() const
Definition: nav.hpp:197
int elem_t
Definition: nav.hpp:310
Cart2D(int ni_, int nj_)
Definition: nav.hpp:305
static const Side ALL[]
Definition: nav.hpp:222
friend std::ostream & operator<<(std::ostream &s, const Coord2D &c)
face_t face_ndx(const coord_t &coord, const Side2D &side)
Definition: nav.hpp:364
Corn3D pivot(Dim3D dim, Dir dir)
Definition: nav.hpp:274
Coord3D coord_t
Definition: nav.hpp:410
static const Dim2D Y
Definition: nav.hpp:128
Type-safe enumeration of axis directions.
Definition: nav.hpp:92
Index tuple in three-dimensional cornerpoint grid.
Definition: nav.hpp:74
coord_t coord(const elem_t &cart_ndx) const
Deconstruct Cartesian index into coordinates.
Definition: nav.hpp:414
friend std::ostream & operator<<(std::ostream &s, const Coord3D &c)
int i() const
Definition: nav.hpp:56
int num_elems() const
Number of (possible) elements in the grid.
Definition: nav.hpp:320
bool operator==(const Dir &rhs) const
Definition: nav.hpp:106
static const Dir INC
Towards the end of the axis with greater numbers.
Definition: nav.hpp:97
Definition: nav.hpp:246
Dir i() const
Definition: nav.hpp:250
Dim dim() const
Definition: nav.hpp:196
Definition: nav.hpp:89
int elem_t
Definition: nav.hpp:411
const Dim m_dim
Definition: nav.hpp:218
Dir(int i)
Private constructor to avoid initialization outside domain.
Definition: nav.hpp:113
bool operator==(const Corn3D &rhs) const
Definition: nav.hpp:285
friend std::ostream & operator<<(std::ostream &os, const Dim2D &d)
static const int COUNT
Definition: nav.hpp:121
static const Side * end()
Definition: nav.hpp:208
const int ni
Definition: nav.hpp:393
bool operator==(const Coord2D &rhs) const
Definition: nav.hpp:62
friend std::ostream & operator<<(std::ostream &os, const Dir &d)
Corn2D(Dir i_, Dir j_)
Definition: nav.hpp:247
Dir k() const
Definition: nav.hpp:280
Dim3D(const Dim2D &rhs)
Definition: nav.hpp:161
Definition: nav.hpp:120
static const Dir DEC
Towards the end of the axis with lesser numbers.
Definition: nav.hpp:94
Cart3D(const UnstructuredGrid &g)
Initialize POD from an existing (3D) grid.
Definition: nav.hpp:398
Dim3D(const Dim3D &rhs)
Definition: nav.hpp:157
node_t node_ndx(const coord_t &coord, const Corn2D &corn)
Definition: nav.hpp:345
const Dir m_dir
Definition: nav.hpp:219
Dim3D(int i)
Definition: nav.hpp:164
Definition: nav.hpp:391
Corn3D(const Corn3D &rhs)
Definition: nav.hpp:264
const int m_j
Definition: nav.hpp:68
const int val
Integer representation suitable for indexing in array.
Definition: nav.hpp:103
bool operator==(const Side< Dim > &rhs) const
Definition: nav.hpp:213
static const int NO_FACE
Definition: nav.hpp:316
static const int NO_NODE
Definition: nav.hpp:317
elem_t cart_ndx(const coord_t &coord) const
Cartesian (flattened) index for a coordinate.
Definition: nav.hpp:325
int k() const
Definition: nav.hpp:80
int num_nodes() const
Definition: nav.hpp:341
static const Side * begin()
Definition: nav.hpp:207
coord_t coord(const elem_t &cart_ndx) const
Cartesian coordinate for a (flattened) index.
Definition: nav.hpp:330
const int nj
Definition: nav.hpp:302
Coord3D(int i_, int j_, int k_)
Definition: nav.hpp:75
Dir(const Dir &rhs)
Definition: nav.hpp:105
Coord2D coord_t
Definition: nav.hpp:309
friend std::ostream & operator<<(std::ostream &os, const Corn3D &c)
int face_t
Definition: nav.hpp:312
const int ni
Definition: nav.hpp:301
int node_t
Definition: nav.hpp:311
Definition: nav.hpp:53