Chombo + EB + MF  3.2
CodimBox.H
Go to the documentation of this file.
1 #ifdef CH_LANG_CC
2 /*
3  * _______ __
4  * / ___/ / ___ __ _ / / ___
5  * / /__/ _ \/ _ \/ V \/ _ \/ _ \
6  * \___/_//_/\___/_/_/_/_.__/\___/
7  * Please refer to Copyright.txt, in Chombo's root directory.
8  */
9 #endif
10 
11 #ifndef _CODIMBOX_H_
12 #define _CODIMBOX_H_
13 #include "BaseFab.H"
14 #include "FArrayBox.H"
15 #include "BoxLayoutData.H"
16 #include "NamespaceHeader.H"
17 
18 /*******************************************************************************
19  */
20 /// An FArrayBox container for storage on the codimensions of a box.
21 /**
22  * The orientation of a box is described by specifying the orthogonal
23  * directions and internally, this is converted to a bit representation.
24  * Direction 'i' is bit 2^i (or via shifting as 1 << i). Directions can be
25  * specified in any order. For example, the edges in 3D orthogonal to
26  * directions i and j may be specified as (0, 1) or (1, 0). Internally, both
27  * are converted to 0x3. Orientations can be described by sequential indices
28  * or bit representations. The routines seq2bit and bit2seq can be used to
29  * switch between the two using lookup tables.
30  *
31  * For example, a 3 dimensional space has the following codimensions, bit
32  * representations, and sequential indices of the orientations:
33  * \verbatim
34  * Codim Bit Integer Sequential numOrient totOrient
35  * Dir zyx
36  * 0 000 0 0 1 0
37  * 1 001 1 0 3 1
38  * 1 010 2 1
39  * 1 100 4 2
40  * 2 011 3 0 3 4
41  * 2 101 5 1
42  * 2 110 6 2
43  * 3 111 7 0 1 7
44  * \endverbatim
45  * The 'indexFAB' and 'bitOrient' are then defined as follows:
46  * \verbatim
47  * indexFAB: 0 0 1 0 2 1 2 0
48  * bitOrient: 0 1 2 4 3 5 6 7
49  * \endverbatim
50  * \note
51  * <ul>
52  * <li> CodimBoxFactory is also defined in this file for use with
53  * BoxLayoutData and similar containers
54  * <li> A FluxBox is essentially a CodimBox with codimension 1.
55  * <li> Not much functionality exists in this class beyond creating and
56  * retrieving the FArrayBoxes.
57  * <li> Codimension 0 is the original object spanning 'SpaceDim' dimensions.
58  * Using this is no different from an FArrayBox itself.
59  * <li> Codimension 'SpaceDim' is a vertex. This is also the same as an
60  * FArrayBox that surrounds all nodes.
61  * </ul>
62  *
63  ******************************************************************************/
64 
65 template <class S >class CodimBox
66 {
67 
68 public:
69  enum
70  {
71  numCD = SpaceDim + 1, ///< Number of codimensions
72  numAI = 1 << SpaceDim ///< Total orientations (array indices) for
73  ///< all codimensions
74  };
75 
76  /// Default constructor
77  CodimBox();
78 
79  /// Full constructor
80  CodimBox(const int a_codim, const Box& a_box, const int a_nvar);
81 
82  /// Destructor
83  ~CodimBox();
84 
85  /// Initialize static lookup tables
86  static void initialize();
87 
88  /// Full define function
89  void define(const int a_codim, const Box& a_box, const int a_nvar);
90 
91  /// Define function
92  void define(const Box& a_box, int a_nvar);
93 
94  /// Deallocate
95  void clear();
96 
97  /// Return the codimension
98  int getCodim() const;
99 
100  /// Number of components
101  int nComp() const;
102 
103  /// Number of different orientations of codimensional objects
104  int getNumOrient() const;
105 
106  /// Number of different orientations of codimensional objects. Used
107  /// externally for any codimension.
108  static int getNumOrient(const int a_codim);
109 
110  /// Switch from a bit orientation to a sequential index of the
111  /// orientation
112  int bit2seq(const unsigned a_bOrient) const;
113 
114  /// Switch from a sequential index to a bit representation of the
115  /// orientation
116  unsigned seq2bit(const int a_iOrient) const;
117 
118  /// Switch from a sequential index to a bit representation of the orientation
119  /// for any codimension
120  static unsigned seq2bit(const int a_codim, const int a_iOrient);
121 
122  /// Get the 'i'th orthogonal direction of an orientation
123  int getDirection(const int a_iOrient, int a_i) const;
124 
125  /// Get all the orthogonal directions of an orientation
126  void getDirections(const int a_iOrient, int *const a_dir) const;
127 
128  /// Get all the orthogonal directions of an orientation. Used externally for
129  /// any codimension.
130  static void getDirections(const int a_codim,
131  const int a_iOrient,
132  int *const a_dir);
133 
134  /// Returns cell-centered box which defines the CodimBox
135  const Box& box() const;
136 
137  /// Returns S in the directions defined by a Box
138  const S& operator()(const Box &a_box) const;
139  S& operator()(const Box &a_box);
140 
141  /// Returns S in the directions defined by an IndexType
142  const S& operator()(const IndexType &a_ixType) const;
143  S& operator()(const IndexType &a_ixType);
144 
145  /// Returns S in the given direction (codimension 0)
146  const S& operator()() const;
147  S& operator()();
148 
149  /// Returns S in the given direction (codimension 1)
150  const S& operator()(const int a_dir0) const;
151  S& operator()(const int a_dir0);
152 
153  /// Returns S in the given direction (codimension 2)
154  const S& operator()(const int a_dir0,
155  const int a_dir1) const;
156  S& operator()(const int a_dir0,
157  const int a_dir1);
158 
159  /// Returns S in the given direction (codimension 3)
160  const S& operator()(const int a_dir0,
161  const int a_dir1,
162  const int a_dir2) const;
163  S& operator()(const int a_dir0,
164  const int a_dir1,
165  const int a_dir2);
166 
167  /// Returns S in the given direction (codimension 4)
168  const S& operator()(const int a_dir0,
169  const int a_dir1,
170  const int a_dir2,
171  const int a_dir3) const;
172  S& operator()(const int a_dir0,
173  const int a_dir1,
174  const int a_dir2,
175  const int a_dir3);
176 
177  /// Returns S in the given direction (codimension 5)
178  const S& operator()(const int a_dir0,
179  const int a_dir1,
180  const int a_dir2,
181  const int a_dir3,
182  const int a_dir4) const;
183  S& operator()(const int a_dir0,
184  const int a_dir1,
185  const int a_dir2,
186  const int a_dir3,
187  const int a_dir4);
188 
189  /// Returns S in the given direction (codimension 6)
190  const S& operator()(const int a_dir0,
191  const int a_dir1,
192  const int a_dir2,
193  const int a_dir3,
194  const int a_dir4,
195  const int a_dir5) const;
196  S& operator()(const int a_dir0,
197  const int a_dir1,
198  const int a_dir2,
199  const int a_dir3,
200  const int a_dir4,
201  const int a_dir5);
202 
203  /// Returns S from a sequential index
204  const S& getSequential(const int a_iOrient) const;
205  S& getSequential(const int a_iOrient);
206 
207  /// Set all values in all FAB
208  void setVal(const Real a_x);
209 
210  /// Orient the stored box in the othogonal directions of the given
211  /// orientation
212  Box orientBox(const int a_iOrient) const;
213 
214  /// Orient a centered box in the othogonal directions of the given
215  /// orientation
216  Box orientBox(const int a_iOrient, const Box& a_cbox) const;
217 
218  /// Orient a centered box in the othogonal directions of the given
219  /// orientation. Used externally for any codimension.
220  static Box orientBox(const int a_codim,
221  const int a_iOrient,
222  const Box& a_cbox);
223 
224  /// Copy from another CodimBox
225  void copy(const Box& a_R,
226  const Interval& a_Cd,
227  const CodimBox& a_src,
228  const Interval& a_Cs);
229 
230  /// Copy from another CodimBox but to a different region
231  void copy(const Box& a_Rs, // Beware that the src and dest arguments
232  const Interval& a_Cd, // are not grouped together
233  const Box& a_Rd,
234  const CodimBox& a_src,
235  const Interval& a_Cs);
236 
237  /// Report preallocation capability as non-static but symmetric
238  static int preAllocatable();
239 
240  /// Returns size of serialized data
241  int size(const Box& a_R, const Interval& a_comps) const;
242 
243  /// Writes a serialized representation of this CodimBox
244  void linearOut(void* a_buf, const Box& a_R, const Interval& a_comps) const;
245 
246  /// Reads a serialized representation of this CodimBox
247  void linearIn(void* a_buf, const Box& a_R, const Interval& a_comps);
248 
249 protected:
250  static int numOrient[numCD]; ///< Number of orientations for an object
251  ///< of a given codimension
252  static int totOrient[numCD]; ///< Total of number of orientations for
253  ///< all smaller codimensions
254  static unsigned bitOrient[CodimBox::numAI];
255  ///< A sequential list of bit
256  ///< representations of possible
257  ///< orientations for each codimension
259  ///< Returns the index of the S
260  ///< for a given codimension and
261  ///< orientation. The input index
262  ///< expresses the orientation as the sum
263  ///< of the orthogonal directions.
264 
265 private:
266 
267  Box m_box; ///< Cell-centered box over which this
268  ///< CodimBox is defined
269  int m_codim; ///< Codimension for which the Ses
270  ///< are defined
271  int m_nvar; ///< Number of components in the S
272  Vector<S*> m_S; ///< The Ses for each orientation
273 
274  // Copy and assignment not allowed
275  CodimBox(const CodimBox&);
276  CodimBox& operator=(const CodimBox&);
277 
278  /// Check that static arrays are initialized
279  static bool isInitialized();
280 
281  /// Return the FArray box from a bit description of the orientation
282  S& getS(const unsigned i);
283  const S& getS(const unsigned i) const;
284 
285  /// Get all the orthogonal directions of an orientation (general)
286  static void genGetDirections(const int a_codim,
287  int a_bOrient,
288  int *const a_dir);
289 
290  /// Orient a centered box in the othogonal directions of the given
291  /// orientation (general)
292  static Box genOrientBox(int a_bOrient, Box a_cbox);
293 
294 // Only of use with a register class
295 // /// Shift all FABs by halves in one direction.
296 // void shiftHalf(const int a_dir, const int a_numHalfs);
297 // friend class LevelCodimRegister;
298 
299 };
300 
301 /*******************************************************************************
302  *
303  * Class CodimBox: inline member definitions
304  *
305  ******************************************************************************/
306 
307 /*--------------------------------------------------------------------*/
308 /// Return the codimension
309 /*--------------------------------------------------------------------*/
310 
311 template<typename S> int CodimBox<S>::getCodim() const
312 {
313  return m_codim;
314 }
315 
316 /*--------------------------------------------------------------------*/
317 /// Number of components
318 /*--------------------------------------------------------------------*/
319 
320 template<typename S> int CodimBox<S>::nComp() const
321 {
322  return m_nvar;
323 }
324 
325 /*--------------------------------------------------------------------*/
326 /// Number of different orientations of codimensional objects
327 /*--------------------------------------------------------------------*/
328 
329 template<typename S> int CodimBox<S>::getNumOrient() const
330 {
331  return numOrient[m_codim];
332 }
333 
334 /*--------------------------------------------------------------------*/
335 /// Number of different orientations of codimensional objects. Used
336 /// externally for any codimension.
337 /*--------------------------------------------------------------------*/
338 
339 template<typename S>int CodimBox<S>::getNumOrient(const int a_codim)
340 {
342  return numOrient[a_codim];
343 }
344 
345 /*--------------------------------------------------------------------*/
346 /// Switch from a bit orientation to a sequential index of the
347 /// orientation
348 /*--------------------------------------------------------------------*/
349 
350 template<typename S> int CodimBox<S>::bit2seq(const unsigned a_bOrient) const
351 {
352  return indexFAB[a_bOrient];
353 }
354 
355 /*--------------------------------------------------------------------*/
356 /// Switch from a sequential index to a bit representation of the
357 /// orientation
358 /*--------------------------------------------------------------------*/
359 
360 template<typename S> unsigned CodimBox<S>::seq2bit(const int a_iOrient) const
361 {
362  return bitOrient[totOrient[m_codim] + a_iOrient];
363 }
364 
365 /*--------------------------------------------------------------------*/
366 /// Switch from a sequential index to a bit representation of the
367 /// orientation for any codimension
368 /*--------------------------------------------------------------------*/
369 
370 template<typename S> unsigned CodimBox<S>::seq2bit(const int a_codim, const int a_iOrient)
371 {
373  return bitOrient[totOrient[a_codim] + a_iOrient];
374 }
375 
376 /*--------------------------------------------------------------------*/
377 /// Get all the orthogonal directions of an orientation
378 /** \param[in] a_iOrient
379  * The sequential orientation index from which to
380  * get the directions
381  * \param[in] a_dir Array with minimum size [m_codim]
382  * \param[out] a_dir Integers defining the directions
383  * 0 <= dir[i] < SpaceDim
384  * \note
385  * <ul>
386  * <li> The directions are orderd from smallest to largest.
387  * </ul>
388  *//*-----------------------------------------------------------------*/
389 
390 template<typename S> void CodimBox<S>::getDirections(const int a_iOrient, int *const a_dir) const
391 {
392  genGetDirections(m_codim, seq2bit(a_iOrient), a_dir);
393 }
394 
395 /*--------------------------------------------------------------------*/
396 /// Get all the orthogonal directions of an orientation. Used
397 /// externally for any codimension.
398 /** \param[in] a_codim
399  * The codimension
400  * \param[in] a_iOrient
401  * The sequential orientation index from which to
402  * get the directions
403  * \param[in] a_dir Array with minimum size [m_codim]
404  * \param[out] a_dir Integers defining the directions
405  * 0 <= dir[i] < SpaceDim
406  * \note
407  * <ul>
408  * <li> The directions are orderd from smallest to largest.
409  * </ul>
410  *//*-----------------------------------------------------------------*/
411 
412 template<typename S> void CodimBox<S>::getDirections(const int a_codim,
413  const int a_iOrient,
414  int *const a_dir)
415 {
417  genGetDirections(a_codim, seq2bit(a_codim, a_iOrient), a_dir);
418 }
419 
420 /*--------------------------------------------------------------------*/
421 // Returns cell-centered box which defines the CodimBox
422 /*--------------------------------------------------------------------*/
423 template<typename S> const Box& CodimBox<S>::box() const
424 {
425  return m_box;
426 }
427 
428 /*--------------------------------------------------------------------*/
429 /// Returns S in the directions defined by a Box
430 /*--------------------------------------------------------------------*/
431 
432 template<typename S> S& CodimBox<S>::operator()(const Box &a_box)
433 {
434  return this->operator()(a_box.ixType());
435 }
436 
437 /*--------------------------------------------------------------------*/
438 /// Returns S from a sequential index
439 /** \param[in] a_iOrient
440  * A sequential orientation index.
441  * \note
442  * <ul>
443  * <li> A bit description of the orientation can be obtained from
444  * \verbatim
445  * bitOrient[totOrient[a_codim] + a_iOrient]
446  * \endverbatim
447  * </ul>
448  *//*-----------------------------------------------------------------*/
449 template<typename S> const S& CodimBox<S>::getSequential(const int a_iOrient) const
450 {
451  CH_assert(a_iOrient < numOrient[m_codim]);
452  return *m_S[a_iOrient];
453 }
454 
455 template<typename S> S& CodimBox<S>::getSequential(const int a_iOrient)
456 {
457  CH_assert(a_iOrient < numOrient[m_codim]);
458  return *m_S[a_iOrient];
459 }
460 
461 /*--------------------------------------------------------------------*/
462 /// Orient the stored box in the othogonal directions of the given
463 /// orientation
464 /** \param[in] a_bOrient
465  * A bit orientation index.
466  *//*-----------------------------------------------------------------*/
467 
468 template<typename S> Box CodimBox<S>::orientBox(const int a_bOrient) const
469 {
470  return orientBox(a_bOrient, m_box);
471 }
472 
473 /*--------------------------------------------------------------------*/
474 /// Orient a centered box in the othogonal directions of the given
475 /// orientation
476 /** \param[in] a_iOrient
477  * A sequential orientation index. This is
478  * converted to a bit orientation for finding the
479  * orthogonal directions.
480  * \param[in] a_cbox
481  * A centered box.
482  * \return The orientated box
483  *//*-----------------------------------------------------------------*/
484 
485 template<typename S> Box CodimBox<S>::orientBox(const int a_iOrient, const Box& a_cbox) const
486 {
487  return genOrientBox(seq2bit(a_iOrient), a_cbox);
488 }
489 
490 /*--------------------------------------------------------------------*/
491 /// Orient a centered box in the othogonal directions of the given
492 /// orientation. Used externally for any codimension.
493 /** \param[in] a_codim
494  * The codimension of the box
495  * \param[in] a_iOrient
496  * A sequential orientation index. This is
497  * converted to a bit orientation for finding the
498  * orthogonal directions.
499  * \param[in] a_cbox
500  * A centered box.
501  * \return The orientated box
502  *//*-----------------------------------------------------------------*/
503 
504 template<typename S> Box CodimBox<S>::orientBox(const int a_codim, const int a_iOrient, const Box& a_cbox)
505 {
507  return genOrientBox(seq2bit(a_codim, a_iOrient), a_cbox);
508 }
509 
510 /*--------------------------------------------------------------------*/
511 /// Report preallocation capability as non-static but symmetric
512 /** The size of the class is dependent upon the codimension. See
513  * BoxLayoutData.H for more info
514  *//*-----------------------------------------------------------------*/
515 
516 template<typename S> int CodimBox<S>::preAllocatable()
517 {
518  return 1;
519 }
520 
521 /*--------------------------------------------------------------------*/
522 /// Check that static arrays are initialized
523 /** Test assumes static arrays have at least been default
524  * initialized.
525  * \return T - Arrays initialized
526  *//*-----------------------------------------------------------------*/
527 
528 template<typename S> bool CodimBox<S>::isInitialized()
529 {
530  return (indexFAB[0] != -1);
531 }
532 
533 /*--------------------------------------------------------------------*/
534 /// Return the FArray box from a bit description of the orientation
535 /** The appropriate FArray box for this codimension and orientation
536  * is given by a query to 'indexFAB'
537  * \param[in] a_bOrient
538  * Bit description of the orientation
539  *//*-----------------------------------------------------------------*/
540 template<typename S> const S& CodimBox<S>::getS(const unsigned a_bOrient) const
541 {
542  return *(m_S[bit2seq(a_bOrient)]);
543 }
544 
545 template<typename S> S& CodimBox<S>::getS(const unsigned a_bOrient)
546 {
547  return *(m_S[bit2seq(a_bOrient)]);
548 }
549 
550 /*******************************************************************************
551  */
552 /// Factory object to create CodimBox(s) for BoxLayoutData and similar
553 /// containers.
554 /*
555  ******************************************************************************/
556 template <class S> class CodimBoxFactory : public DataFactory<CodimBox<S> >
557 {
558 
559 public:
560  /// Constructor stores codimension
561  CodimBoxFactory(int a_codim)
562  :
563  m_codim(a_codim)
564  { }
565 
566  /// Create a new CodimBox
567  CodimBox<S>* create(const Box& a_box,
568  int a_ncomps,
569  const DataIndex& a_datInd) const
570  {
571  return new CodimBox<S>(m_codim, a_box, a_ncomps);
572  }
573 
574 private:
575  int m_codim; ///< Codimension
576 
577 };
578 
579 #include "NamespaceFooter.H"
580 
581 #include "CodimBoxImplem.H"
582 
583 #endif
int getNumOrient() const
Number of different orientations of codimensional objects.
Definition: CodimBox.H:329
~CodimBox()
Destructor.
Definition: CodimBoxImplem.H:82
unsigned seq2bit(const int a_iOrient) const
Definition: CodimBox.H:360
#define CH_assert(cond)
Definition: CHArray.H:37
const S & operator()() const
Returns S in the given direction (codimension 0)
Definition: CodimBoxImplem.H:303
one dimensional dynamic array
Definition: Vector.H:53
Number of codimensions.
Definition: CodimBox.H:71
static int totOrient[numCD]
Definition: CodimBox.H:252
static unsigned bitOrient[CodimBox::numAI]
Definition: CodimBox.H:254
static void initialize()
Initialize static lookup tables.
Definition: CodimBoxImplem.H:101
int getCodim() const
Return the codimension.
Definition: CodimBox.H:311
int bit2seq(const unsigned a_bOrient) const
Definition: CodimBox.H:350
int size(const Box &a_R, const Interval &a_comps) const
Returns size of serialized data.
Definition: CodimBoxImplem.H:648
Vector< S * > m_S
The Ses for each orientation.
Definition: CodimBox.H:272
CodimBoxFactory(int a_codim)
Constructor stores codimension.
Definition: CodimBox.H:561
const int SpaceDim
Definition: SPACE.H:38
static int numOrient[numCD]
Definition: CodimBox.H:250
CodimBox & operator=(const CodimBox &)
Structure for passing component ranges in code.
Definition: Interval.H:23
Definition: CodimBox.H:556
void linearOut(void *a_buf, const Box &a_R, const Interval &a_comps) const
Writes a serialized representation of this CodimBox.
Definition: CodimBoxImplem.H:672
double Real
Definition: REAL.H:33
IndexType ixType() const
centering
Definition: Box.H:1798
int m_nvar
Number of components in the S.
Definition: CodimBox.H:271
int nComp() const
Number of components.
Definition: CodimBox.H:320
static Box genOrientBox(int a_bOrient, Box a_cbox)
Definition: CodimBoxImplem.H:760
void copy(const Box &a_R, const Interval &a_Cd, const CodimBox &a_src, const Interval &a_Cs)
Copy from another CodimBox.
Definition: CodimBoxImplem.H:559
static void genGetDirections(const int a_codim, int a_bOrient, int *const a_dir)
Get all the orthogonal directions of an orientation (general)
Definition: CodimBoxImplem.H:731
int m_codim
Definition: CodimBox.H:269
void linearIn(void *a_buf, const Box &a_R, const Interval &a_comps)
Reads a serialized representation of this CodimBox.
Definition: CodimBoxImplem.H:695
Definition: CodimBox.H:72
CodimBox< S > * create(const Box &a_box, int a_ncomps, const DataIndex &a_datInd) const
Create a new CodimBox.
Definition: CodimBox.H:567
int m_codim
Codimension.
Definition: CodimBox.H:575
const Box & box() const
Returns cell-centered box which defines the CodimBox.
Definition: CodimBox.H:423
A Rectangular Domain on an Integer Lattice.
Definition: Box.H:469
void clear()
Deallocate.
Definition: CodimBoxImplem.H:193
An FArrayBox container for storage on the codimensions of a box.
Definition: CodimBox.H:65
S & getS(const unsigned i)
Return the FArray box from a bit description of the orientation.
Definition: CodimBox.H:545
Definition: DataIndex.H:114
int getDirection(const int a_iOrient, int a_i) const
Get the &#39;i&#39;th orthogonal direction of an orientation.
Definition: CodimBoxImplem.H:222
Cell-Based or Node-Based Indices.
Definition: Box.H:45
void define(const int a_codim, const Box &a_box, const int a_nvar)
Full define function.
Definition: CodimBoxImplem.H:159
Factory object to data members of a BoxLayoutData container.
Definition: BoxLayoutData.H:30
static int preAllocatable()
Report preallocation capability as non-static but symmetric.
Definition: CodimBox.H:516
void getDirections(const int a_iOrient, int *const a_dir) const
Get all the orthogonal directions of an orientation.
Definition: CodimBox.H:390
void setVal(const Real a_x)
Set all values in all FAB.
Definition: CodimBoxImplem.H:529
const S & getSequential(const int a_iOrient) const
Returns S from a sequential index.
Definition: CodimBox.H:449
static int indexFAB[CodimBox::numAI]
Definition: CodimBox.H:258
Box m_box
Definition: CodimBox.H:267
CodimBox()
Default constructor.
Definition: CodimBoxImplem.H:57
Box orientBox(const int a_iOrient) const
Definition: CodimBox.H:468
static bool isInitialized()
Check that static arrays are initialized.
Definition: CodimBox.H:528