openCARP
Doxygen code documentation for the open cardiac electrophysiology simulator openCARP
SF_container.h
Go to the documentation of this file.
1 // ----------------------------------------------------------------------------
2 // openCARP is an open cardiac electrophysiology simulator.
3 //
4 // Copyright (C) 2020 openCARP project
5 //
6 // This program is licensed under the openCARP Academic Public License (APL)
7 // v1.0: You can use and redistribute it and/or modify it in non-commercial
8 // academic environments under the terms of APL as published by the openCARP
9 // project v1.0, or (at your option) any later version. Commercial use requires
10 // a commercial license (info@opencarp.org).
11 //
12 // This program is distributed without any warranty; see the openCARP APL for
13 // more details.
14 //
15 // You should have received a copy of the openCARP APL along with this program
16 // and can find it online: http://www.opencarp.org/license
17 // ----------------------------------------------------------------------------
18 
27 #ifndef _SF_CONTAINER_H
28 #define _SF_CONTAINER_H
29 
30 #include <cstring>
31 #include <mpi.h>
32 #include <map>
33 #include <math.h>
34 #include <set>
35 
36 #include "dense_mat.hpp"
37 #include "SF_globals.h"
38 #include "SF_vector.h"
39 #include "SF_linalg_utils.h"
40 #include "hashmap.hpp"
41 
42 // This datatypes will be used in conjunction with mesh data. We might want to
43 // have increased / reduced precision when storing meshes, mesh related numberings, etc.
44 // Therefore, we will use (mesh_int_t,mesh_real_t) for data fields that scale with the mesh size,
45 // to be able to tweak the used datatype later. -Aurel
46 typedef int mesh_int_t;
47 typedef float mesh_real_t;
48 
49 namespace SF {
50 
52 enum elem_t
53 {
54  Tetra = 0,
60  Tri,
62 };
63 
65 struct Point {
66  double x;
67  double y;
68  double z;
69 };
70 
71 template<class V>
72 inline Point arr_to_point(V* arr)
73 {
74  return {arr[0], arr[1], arr[2]};
75 }
76 
77 template<class V>
78 inline void point_to_arr(Point & p, V* arr)
79 {
80  arr[0] = p.x, arr[1] = p.y, arr[2] = p.z;
81 }
82 
84 inline Point cross(const Point & a, const Point & b)
85 {
86  Point c = {a.y*b.z - b.y*a.z, b.x*a.z - a.x*b.z, a.x*b.y - a.y*b.x};
87  return c;
88 }
89 
90 inline double inner_prod(const Point & a, const Point & b)
91 {
92  return a.x*b.x + a.y*b.y + a.z*b.z;
93 }
94 
95 inline void outer_prod(const Point & a, const Point & b, const double s, double* buff, const bool add = false)
96 {
97  if(add == false)
98  memset(buff, 0, 9*sizeof(double));
99 
100  buff[0] += a.x*b.x*s, buff[1] += a.x*b.y*s, buff[2] += a.x*b.z*s;
101  buff[3] += a.y*b.x*s, buff[4] += a.y*b.y*s, buff[5] += a.y*b.z*s;
102  buff[6] += a.z*b.x*s, buff[7] += a.z*b.y*s, buff[8] += a.z*b.z*s;
103 }
104 
105 inline void outer_prod(const Point & a, const Point & b, double* buff)
106 {
107  outer_prod(a, b, 1.0, buff);
108 }
109 
111 inline double mag(const Point & vect)
112 {
113  return sqrt(inner_prod(vect, vect));
114 }
115 
116 inline Point normalize(const Point & vect)
117 {
118  double norm = mag(vect);
119  return {vect.x / norm, vect.y / norm, vect.z / norm};
120 }
121 
122 inline Point operator-(const Point & a, const Point & b)
123 {
124  return {a.x - b.x, a.y - b.y, a.z - b.z};
125 }
126 
127 inline Point operator+(const Point & a, const Point & b)
128 {
129  return {a.x + b.x, a.y + b.y, a.z + b.z};
130 }
131 
132 inline Point operator*(const Point & a, const double & s)
133 {
134  return {a.x * s, a.y * s, a.z * s};
135 }
136 
138 inline Point project(const Point & a, const Point & b)
139 {
140  return a * inner_prod(normalize(a), normalize(b));
141 }
142 
143 inline Point orthogonalize(const Point & a, const Point & b)
144 {
145  return a - project(a, b);
146 }
147 
148 
149 inline double distance(const Point & a, const Point & b)
150 {
151  return mag(a - b);
152 }
153 
155 inline elem_t getElemTypeID(char *eletype)
156 {
157  elem_t ret;
158 
159  if ( !strcmp( eletype, "Tt" ) ) {
160  ret = Tetra;
161  } else if ( !strcmp( eletype, "Hx" ) ) {
162  ret = Hexa;
163  } else if ( !strcmp( eletype, "Oc" ) ) {
164  ret = Octa;
165  } else if ( !strcmp( eletype, "Py" ) ) {
166  ret = Pyramid;
167  } else if ( !strcmp( eletype, "Pr" ) ) {
168  ret = Prism;
169  } else if ( !strcmp( eletype, "Qd" ) ) {
170  ret = Quad;
171  } else if ( !strcmp( eletype, "Tr" ) ) {
172  ret = Tri;
173  } else {
174  ret = Line;
175  }
176  return ret;
177 }
178 
179 template<class S, class POINT> inline
180 void array_to_points(const vector<S> & arr, vector<POINT> & pts)
181 {
182  pts.resize(arr.size() / 3);
183  for(size_t i=0; i<pts.size(); i++)
184  pts[i] = {arr[i*3+0], arr[i*3+1], arr[i*3+2]};
185 }
186 
188 typedef enum {
194 } SF_nbr;
195 
196 // forward declaration of parallel layouts since they are used in mesh.
197 template<class T> class overlapping_layout;
198 template<class T> class non_overlapping_layout;
199 
206 template<class T>
208 {
209  private:
212 
213  public:
216  {}
217 
224  index_mapping(const vector<T> & a, const vector<T> & b)
225  {
226  this->assign(a, b);
227  }
228 
235  inline void assign(const vector<T> & a, const vector<T> & b)
236  {
237  // a 1:1 mapping between old and new indices is required
238  assert( a.size() == b.size() );
239 
240  _fwd.clear();
241  _bwd.clear();
242 
243  for(size_t i=0; i<a.size(); i++)
244  {
245  T aidx = a[i], bidx = b[i];
246  _fwd[aidx] = bidx;
247  _bwd[bidx] = aidx;
248  }
249  }
250 
252  inline T forward_map(T idx) const
253  {
254  typename hashmap::unordered_map<T, T>::const_iterator it = _fwd.find(idx);
255  if(it != _fwd.end())
256  return it->second;
257  else
258  return T(-1);
259  }
260 
262  inline T backward_map(T idx) const
263  {
264  typename hashmap::unordered_map<T, T>::const_iterator it = _bwd.find(idx);
265  if(it != _bwd.end())
266  return it->second;
267  else
268  return T(-1);
269  }
270 
271 
280  inline void forward_map(vector<T> & idx) const
281  {
282  size_t lsize = idx.size();
283  vector<T> perm(lsize);
284  interval(perm, 0, lsize);
285 
286  binary_sort_copy(idx, perm);
287 
288  size_t c = 0;
290 
291  while(c < lsize)
292  {
293  T cc = idx[c];
294  it = _fwd.find(cc);
295 
296  T val = it != _fwd.end() ? it->second : T(-1);
297 
298  while( (c < lsize) && (cc == idx[c]) )
299  {
300  idx[c] = val;
301  c++;
302  }
303  }
304 
305  binary_sort_copy(perm, idx);
306  }
307 
316  inline void backward_map(vector<T> & idx) const
317  {
318  size_t lsize = idx.size();
319  vector<T> perm(lsize);
320  interval(perm, 0, lsize);
321 
322  binary_sort_copy(idx, perm);
323 
324  size_t c = 0;
326 
327  while(c < lsize)
328  {
329  T cc = idx[c];
330  it = _bwd.find(cc);
331 
332  T val = it != _bwd.end() ? *it : T(-1);
333 
334  while( (c < lsize) && (cc == idx[c]) )
335  {
336  idx[c] = val;
337  c++;
338  }
339  }
340 
341  binary_sort_copy(perm, idx);
342  }
343 
345  size_t size() const
346  {
347  return _fwd.size();
348  }
350  bool in_a(const T idx) {
351  return _fwd.count(idx) == 1;
352  }
354  bool in_b(const T idx) {
355  return _bwd.count(idx) == 1;
356  }
357 
359  {
360  return _fwd;
361  }
362 
364  {
365  return _bwd;
366  }
367 
369  {
370  return _fwd;
371  }
372 
374  {
375  return _bwd;
376  }
377 };
378 
382 template<class T, class S>
383 class meshdata
384 {
385 public:
386  size_t g_numelem;
387  size_t l_numelem;
388  size_t g_numpts;
389  size_t l_numpts;
390 
392  MPI_Comm comm;
393 
395  std::string name;
396 
397  // element connectivity : the nodes forming the elements
401 
402  // element data
403  // one value per element
407  // multiple values per element
410 
413 
414  std::map< SF_nbr, vector<T> > nbr;
416 
419 
421  meshdata(): g_numelem(0), l_numelem(0), g_numpts(0), l_numpts(0),
422  comm(SF_COMM), name("unnamed")
423  {}
424 
432  inline vector<T> & register_numbering(SF_nbr nbr_type)
433  {
434  if(nbr.count(nbr_type) == 0)
435  nbr[nbr_type] = vector<T>();
436 
437  return nbr[nbr_type];
438  }
439 
452  inline vector<T> & get_numbering(SF_nbr nbr_type)
453  {
454  typename std::map< SF_nbr, vector<T> >::iterator it = nbr.find(nbr_type);
455  assert(it != nbr.end());
456  return it->second;
457  }
470  inline const vector<T> & get_numbering(SF_nbr nbr_type) const
471  {
472  typename std::map< SF_nbr, vector<T> >::const_iterator it = nbr.find(nbr_type);
473  assert(it != nbr.end());
474  return it->second;
475  }
476 
484  inline void localize(SF_nbr nbr_type)
485  {
486  // register numbering
487  vector<T> & nod = this->register_numbering(nbr_type);
488 
490  for(const T & c : this->con) g2l[c] = 0;
491  g2l.sort();
492 
493  // compute numbering
494  nod.resize(g2l.size());
495 
496  size_t widx = 0;
497  for(auto it = g2l.begin(); it != g2l.end(); ++it, widx++) {
498  nod[widx] = it->first;
499  it->second = widx;
500  }
501 
502  global_to_local(g2l, this->con, true);
503  this->l_numpts = nod.size();
504  }
505 
513  inline void globalize(SF_nbr nbr_type)
514  {
515  // register numbering
516  vector<T> & nod = this->get_numbering(nbr_type);
517  for(T & c : con) c = nod[c];
518  }
519 
520 
526  inline void generate_par_layout()
527  {
528  const vector<T> & rnod = this->get_numbering(NBR_REF);
529  const vector<T> & reidx = this->get_numbering(NBR_ELEM_REF);
530 
531  pl.assign(rnod, comm);
532  g_numpts = pl.num_global_idx();
533 
534  epl.assign(reidx, comm);
535  }
536 
540  inline void clear_data()
541  {
542  g_numelem = 0;
543  g_numpts = 0;
544  l_numelem = 0;
545  l_numpts = 0;
546 
547  con.resize(0); con.reallocate();
548  dsp.resize(0); dsp.reallocate();
549  tag.resize(0); tag.reallocate();
550  type.resize(0); type.reallocate();
551 
552  fib.resize(0); fib.reallocate();
553  she.resize(0); she.reallocate();
554  xyz.resize(0); xyz.reallocate();
555 
556  extr_tag.clear();
557  nbr.clear();
558  }
559 
560 
561 };
562 
570 template<class T, class S>
571 inline void nodal_connectivity_graph(const meshdata<T, S> & mesh,
572  vector<T> & n2n_cnt,
573  vector<T> & n2n_con)
574 {
575  vector<T> e2n_cnt, n2e_cnt, n2e_con;
576  const vector<T> & e2n_con = mesh.con;
577 
578  cnt_from_dsp(mesh.dsp, e2n_cnt);
579 
580  transpose_connectivity(e2n_cnt, e2n_con, n2e_cnt, n2e_con);
581  multiply_connectivities(n2e_cnt, n2e_con,
582  e2n_cnt, e2n_con,
583  n2n_cnt, n2n_con);
584 }
585 
595 template<class T, class S>
597 {
598  vector<T> n2n_cnt, n2n_con;
599  nodal_connectivity_graph(mesh, n2n_cnt, n2n_con);
600 
601  int nmax = 0;
602  for(size_t nidx=0; nidx < n2n_cnt.size(); nidx++)
603  if(nmax < n2n_cnt[nidx]) nmax = n2n_cnt[nidx];
604 
605  MPI_Allreduce(MPI_IN_PLACE, &nmax, 1, MPI_INT, MPI_MAX, mesh.comm);
606 
607  return nmax;
608 }
609 
610 template<class T, class S>
611 void get_alg_mask(const meshdata<T,S> & mesh, vector<bool> & alg_mask)
612 {
613  const vector<T> & alg_nod = mesh.pl.algebraic_nodes();
614 
615  alg_mask.assign(mesh.l_numpts, false);
616  for(const T & n : alg_nod) alg_mask[n] = true;
617 }
618 
619 
624 template<class T>
626 {
627  public:
632 
634  inline void resize(size_t size)
635  {
636  scnt.assign(size, T()), rcnt.assign(size, T()), sdsp.assign(size+1, T()), rdsp.assign(size+1, T());
637  }
638 
640  template<class V>
641  inline void scale(V fac)
642  {
643  for(size_t i=0; i<scnt.size(); i++)
644  scnt[i] *= fac, rcnt[i] *= fac;
645 
646  for(size_t i=0; i<sdsp.size(); i++)
647  sdsp[i] *= fac, rdsp[i] *= fac;
648  }
649 
651  inline void transpose()
652  {
653  vector<T> tcnt(scnt), tdsp(sdsp);
654  scnt = rcnt, sdsp = rdsp;
655  rcnt = tcnt, rdsp = tdsp;
656  }
657 
666  template<class V>
667  inline void configure(const vector<V> & dest, MPI_Comm comm)
668  {
669  int size, rank;
670  MPI_Comm_size(comm, &size); MPI_Comm_rank(comm, &rank);
671 
672  this->resize(size);
673 
674  count(dest, scnt);
675  MPI_Alltoall(scnt.data(), sizeof(T), MPI_BYTE, rcnt.data(), sizeof(T), MPI_BYTE, comm);
676  dsp_from_cnt(scnt, sdsp);
677  dsp_from_cnt(rcnt, rdsp);
678  }
688  template<class V>
689  inline void configure(const vector<V> & dest, const vector<T> & cnt, MPI_Comm comm)
690  {
691  int size, rank;
692  MPI_Comm_size(comm, &size); MPI_Comm_rank(comm, &rank);
693 
694  this->resize(size);
695 
696  scnt.zero();
697  for(size_t i=0; i<dest.size(); i++) scnt[dest[i]] += cnt[i];
698 
699  MPI_Alltoall(scnt.data(), sizeof(T), MPI_BYTE, rcnt.data(), sizeof(T), MPI_BYTE, comm);
700 
701  dsp_from_cnt(scnt, sdsp);
702  dsp_from_cnt(rcnt, rdsp);
703  }
713  template<class V>
714  inline void source_ranks(vector<V> & source)
715  {
716  size_t size = rcnt.size();
717  source.resize(sum(rcnt));
718 
719  for(size_t i=0, widx=0; i<size; i++)
720  for(T j=0; j<rcnt[i]; j++, widx++)
721  source[widx] = i;
722  }
723 };
724 
725 template<class T>
726 struct tuple {
727  T v1;
728  T v2;
729 };
730 
731 template<class T, class S>
733 {
734  T v1;
735  S v2;
736 };
737 
738 template<class T>
739 struct triple {
740  T v1;
741  T v2;
742  T v3;
743 };
744 
745 template<class T, class S, class V>
746 struct mixed_triple {
747  T v1;
748  S v2;
749  V v3;
750 };
751 
752 template<class T>
753 struct quadruple {
754  T v1;
755  T v2;
756  T v3;
757  T v4;
758 };
759 
760 template<class T>
761 bool operator<(const struct tuple<T> & lhs, const struct tuple<T> & rhs)
762 {
763  if(lhs.v1 != rhs.v1)
764  return lhs.v1 < rhs.v1;
765  else
766  return lhs.v2 < rhs.v2;
767 }
768 template<class T, class S>
769 bool operator<(const struct mixed_tuple<T, S> & lhs, const struct mixed_tuple<T, S> & rhs)
770 {
771  if(lhs.v1 != rhs.v1)
772  return lhs.v1 < rhs.v1;
773  else
774  return lhs.v2 < rhs.v2;
775 }
776 
777 template<class T>
778 bool operator<(const struct triple<T> & lhs, const struct triple<T> & rhs)
779 {
780  if(lhs.v1 != rhs.v1)
781  return lhs.v1 < rhs.v1;
782  else if(lhs.v2 != rhs.v2)
783  return lhs.v2 < rhs.v2;
784  else
785  return lhs.v3 < rhs.v3;
786 }
787 
788 template<class T>
789 bool operator<(const struct quadruple<T> & lhs, const struct quadruple<T> & rhs)
790 {
791  if(lhs.v1 != rhs.v1)
792  return lhs.v1 < rhs.v1;
793  else if(lhs.v2 != rhs.v2)
794  return lhs.v2 < rhs.v2;
795  else if(lhs.v3 != rhs.v3)
796  return lhs.v3 < rhs.v3;
797  else
798  return lhs.v4 < rhs.v4;
799 }
800 
801 // expand hashing for custom triple struct
802 
803 }
804 
805 namespace hashmap {
806 
807 template<typename T>
808 struct hash_ops< SF::tuple<T> >
809 {
810  static inline
812  return a.v1 == b.v1 && a.v2 == b.v2;
813  }
814 
815  static inline
820  return h;
821  }
822 };
823 
824 template<typename T>
825 struct hash_ops< SF::triple<T> >
826 {
827  static inline
829  return a.v1 == b.v1 && a.v2 == b.v2 && a.v3 == b.v3;
830  }
831 
832  static inline
834  hm_uint h = mkhash_init;
838  return h;
839  }
840 };
841 
842 template<typename T>
843 struct hash_ops< SF::quadruple<T> >
844 {
845  static inline
847  return a.v1 == b.v1 && a.v2 == b.v2 && a.v3 == b.v3 && a.v4 == b.v4;
848  }
849 
850  static inline
852  hm_uint h = mkhash_init;
857  return h;
858  }
859 };
860 }
861 
862 template<class T>
863 struct tri_sele {
864  T v1;
865  T v2;
866  T v3;
867  T eidx;
868 };
869 
870 template<class T>
871 struct quad_sele {
872  T v1;
873  T v2;
874  T v3;
875  T v4;
876  T eidx;
877 };
878 
880 template<class T>
881 void sort_triple(const T in1, const T in2, const T in3, T & out1, T & out2, T & out3)
882 {
883  bool t12 = in1 < in2;
884  bool t13 = in1 < in3;
885  bool t23 = in2 < in3;
886 
887  if(t12) {
888  //(123),(312),(132)
889  if(t23) {
890  //123
891  out1=in1; out2=in2; out3=in3;
892  }
893  else {
894  //(312),(132)
895  if(t13) {
896  //132
897  out1=in1; out2=in3; out3=in2;
898  }
899  else {
900  //312
901  out1=in3; out2=in1; out3=in2;
902  }
903  }
904  }
905  else {
906  //(213),(231),(321)
907  if(t23) {
908  //(213),(231)
909  if(t13) {
910  //213
911  out1=in2; out2=in1; out3=in3;
912  }
913  else {
914  //231
915  out1=in2; out2=in3; out3=in1;
916  }
917  }
918  else {
919  //321
920  out1=in3; out2=in2; out3=in1;
921  }
922  }
923 }
924 
925 #endif
926 
void generate_par_layout()
Set up the parallel layout.
Definition: SF_container.h:526
Definition: dense_mat.hpp:34
The mesh storage class. It contains both element and vertex data.
Definition: SF_container.h:383
hm_uint mkhash(hm_uint a, hm_uint b)
Definition: hashmap.hpp:52
The vector class and related algorithms.
non_overlapping_layout< T > epl
element parallel layout
Definition: SF_container.h:418
vector< T > & get_numbering(SF_nbr nbr_type)
Get the vector defining a certain numbering.
Definition: SF_container.h:452
double z
Definition: SF_container.h:68
Point normalize(const Point &vect)
Definition: SF_container.h:116
void sort_triple(const T in1, const T in2, const T in3, T &out1, T &out2, T &out3)
sort the "in" triple into the "out" triple
Definition: SF_container.h:881
Point arr_to_point(V *arr)
Definition: SF_container.h:72
void multiply_connectivities(const vector< T > &a_cnt, const vector< T > &a_con, const vector< T > &b_cnt, const vector< T > &b_con, vector< T > &c_cnt, vector< T > &c_con)
unsigned long int hm_uint
Definition: hashmap.hpp:43
void zero()
Definition: SF_vector.h:248
static hm_uint hash(SF::tuple< T > a)
Definition: SF_container.h:816
MPI_Comm comm
the parallel mesh is defined on a MPI world
Definition: SF_container.h:392
Definition: mesher.cc:237
Dense matrix class and associated funcs.
float mesh_real_t
Definition: SF_container.h:47
vector< T > tag
element tag
Definition: SF_container.h:405
static hm_uint hash(SF::triple< T > a)
Definition: SF_container.h:833
PETSc numbering of nodes.
Definition: SF_container.h:191
vector< T > dsp
connectivity starting index of each element
Definition: SF_container.h:404
Point orthogonalize(const Point &a, const Point &b)
Definition: SF_container.h:143
void interval(vector< T > &vec, size_t start, size_t end)
Create an integer interval between start and end.
Definition: SF_vector.h:350
T backward_map(T idx) const
Map one index from b to a.
Definition: SF_container.h:262
overlapping_layout< T > pl
nodal parallel layout
Definition: SF_container.h:417
vector< S > fib
fiber direction
Definition: SF_container.h:408
void resize(size_t size)
Resize all vectors to size.
Definition: SF_container.h:634
void array_to_points(const vector< S > &arr, vector< POINT > &pts)
Definition: SF_container.h:180
The nodal numbering of the reference mesh (the one stored on HD).
Definition: SF_container.h:189
std::map< SF_nbr, vector< T > > nbr
container for different numberings
Definition: SF_container.h:414
void count(const vector< T > &data, vector< S > &cnt)
Count number of occurrences of indices.
Definition: SF_vector.h:332
double inner_prod(const Point &a, const Point &b)
Definition: SF_container.h:90
index_mapping()
empty constructor.
Definition: SF_container.h:215
vector< T > rdsp
Displacements w.r.t. rcnt.
Definition: SF_container.h:631
dmat< S > operator-(const dmat< S > &a, const dmat< S > &b)
Definition: dense_mat.hpp:421
Sequential linear algebra kernels.
vector< S > xyz
node cooridnates
Definition: SF_container.h:415
T * data()
Pointer to the vector&#39;s start.
Definition: SF_vector.h:91
vector< T > con
Definition: SF_container.h:400
void point_to_arr(Point &p, V *arr)
Definition: SF_container.h:78
Point and vector struct.
Definition: SF_container.h:65
const vector< T > & get_numbering(SF_nbr nbr_type) const
Get the vector defining a certain numbering.
Definition: SF_container.h:470
SF_nbr
Enumeration encoding the different supported numberings.
Definition: SF_container.h:188
void transpose_connectivity(const vector< T > &a_cnt, const vector< T > &a_con, vector< T > &b_cnt, vector< T > &b_con)
Transpose CRS matrix graph A into B.
#define SF_COMM
the default SlimFem MPI communicator
Definition: SF_globals.h:27
int mesh_int_t
Definition: SF_container.h:46
The element numbering of the reference mesh (the one stored on HD).
Definition: SF_container.h:192
const hashmap::unordered_map< T, T > & get_bwd_map() const
Definition: SF_container.h:363
Submesh nodal numbering: The globally ascending sorted reference indices are reindexed.
Definition: SF_container.h:190
void get_alg_mask(const meshdata< T, S > &mesh, vector< bool > &alg_mask)
Definition: SF_container.h:611
int max_nodal_edgecount(const meshdata< T, S > &mesh)
Compute the maximum number of node-to-node edges for a mesh.
Definition: SF_container.h:596
The class holds the communication graph for a MPI_Exchange() call.
Definition: SF_container.h:625
Base hashing class.
Definition: hashmap.hpp:87
Point project(const Point &a, const Point &b)
project b onto a
Definition: SF_container.h:138
double distance(const Point &a, const Point &b)
Definition: SF_container.h:149
void sort(Compare comp=Compare())
Sort data entries.
Definition: hashmap.hpp:659
void cnt_from_dsp(const vector< T > &dsp, vector< T > &cnt)
Compute counts from displacements.
Definition: SF_vector.h:319
void configure(const vector< V > &dest, const vector< T > &cnt, MPI_Comm comm)
Set up the communication graph.
Definition: SF_container.h:689
void clear_data()
Clear the mesh data from memory.
Definition: SF_container.h:540
Submesh element numbering: The globally ascending sorted reference indices are reindexed.
Definition: SF_container.h:193
hashmap::unordered_set< int > extr_tag
the element tags based on which the mesh has been extracted
Definition: SF_container.h:412
elem_t getElemTypeID(char *eletype)
Generate element type enum from string.
Definition: SF_container.h:155
size_t size() const
Definition: hashmap.hpp:687
bool in_b(const T idx)
return whether idx is in set B
Definition: SF_container.h:354
static bool cmp(SF::tuple< T > a, SF::tuple< T > b)
Definition: SF_container.h:811
void configure(const vector< V > &dest, MPI_Comm comm)
Set up the communication graph.
Definition: SF_container.h:667
T sum(const vector< T > &vec)
Compute sum of a vector&#39;s entries.
Definition: SF_vector.h:340
dmat< S > operator+(const dmat< S > &a, const dmat< S > &b)
Definition: dense_mat.hpp:413
meshdata()
construct empty mesh
Definition: SF_container.h:421
static hm_uint hash(SF::quadruple< T > a)
Definition: SF_container.h:851
void reallocate()
Definition: SF_vector.h:257
dmat< S > operator*(const dmat< S > &a, const dmat< S > &b)
Definition: dense_mat.hpp:373
static bool cmp(SF::quadruple< T > a, SF::quadruple< T > b)
Definition: SF_container.h:846
void binary_sort_copy(vector< T > &_V, vector< S > &_W)
Definition: SF_sort.h:296
Index mapping class. This is a bijective mapping.
Definition: SF_container.h:207
void global_to_local(const vector< T > &glob, vector< T > &data, bool sortedData, bool doWarn)
Definition: SF_sort.h:540
hashmap::unordered_map< T, T > & get_bwd_map()
Definition: SF_container.h:373
elem_t
element type enum
Definition: SF_container.h:52
void scale(V fac)
scale comm graph layout data
Definition: SF_container.h:641
void outer_prod(const Point &a, const Point &b, const double s, double *buff, const bool add=false)
Definition: SF_container.h:95
static bool cmp(SF::triple< T > a, SF::triple< T > b)
Definition: SF_container.h:828
void localize(SF_nbr nbr_type)
Localize the connectivity data w.r.t. a given numbering.
Definition: SF_container.h:484
std::string name
the mesh name
Definition: SF_container.h:395
hm_int count(const K &key) const
Check if key exists.
Definition: hashmap.hpp:579
size_t size() const
The current size of the vector.
Definition: SF_vector.h:104
vector< T > scnt
Number of elements sent to each rank.
Definition: SF_container.h:628
void nodal_connectivity_graph(const meshdata< T, S > &mesh, vector< T > &n2n_cnt, vector< T > &n2n_con)
Compute the node-to-node connectivity.
Definition: SF_container.h:571
The parallel layout of non overlapping indices.
Definition: SF_container.h:198
vector< T > sdsp
Displacements w.r.t. scnt.
Definition: SF_container.h:629
size_t num_global_idx() const
Retrieve the global number of indices.
index_mapping(const vector< T > &a, const vector< T > &b)
Constructor that uses assign() to set up the index mapping.
Definition: SF_container.h:224
const hm_uint mkhash_init
Definition: hashmap.hpp:57
void assign(const vector< T > &a, const vector< T > &b)
Set up the index mapping between a and b.
Definition: SF_container.h:235
size_t l_numpts
local number of points
Definition: SF_container.h:389
hashmap::unordered_map< T, T > & get_fwd_map()
Definition: SF_container.h:368
double x
Definition: SF_container.h:66
void assign(const vector< T > &idx, MPI_Comm comm)
Initialization function.
double y
Definition: SF_container.h:67
size_t l_numelem
local number of elements
Definition: SF_container.h:387
size_t g_numpts
global number of points
Definition: SF_container.h:388
void forward_map(vector< T > &idx) const
Map a whole array of indices in a to indices in b.
Definition: SF_container.h:280
void backward_map(vector< T > &idx) const
Map a whole array of indices in b to indices in a.
Definition: SF_container.h:316
void assign(InputIterator s, InputIterator e)
Assign a memory range.
Definition: SF_vector.h:161
void source_ranks(vector< V > &source)
For every received data element, get the rank indices it was receive from.
Definition: SF_container.h:714
iterator find(const K &key)
Search for key. Return iterator.
Definition: hashmap.hpp:593
T forward_map(T idx) const
Map one index from a to b.
Definition: SF_container.h:252
vector< S > she
sheet direction
Definition: SF_container.h:409
bool in_a(const T idx)
return whether idx is in set A
Definition: SF_container.h:350
void transpose()
transpose comm graph (receive becomes send, and vice versa)
Definition: SF_container.h:651
size_t g_numelem
global number of elements
Definition: SF_container.h:386
const hashmap::unordered_map< T, T > & get_fwd_map() const
Definition: SF_container.h:358
vector< T > rcnt
Number of elements received from each rank.
Definition: SF_container.h:630
vector< T > & register_numbering(SF_nbr nbr_type)
Register a new numbering to the mesh and return the associated index vector.
Definition: SF_container.h:432
void assign(const vector< T > &ref_eidx, MPI_Comm comm)
Generate the layout.
size_t size() const
number of entries in bijective map
Definition: SF_container.h:345
Point cross(const Point &a, const Point &b)
cross product
Definition: SF_container.h:84
void resize(size_t n)
Resize a vector.
Definition: SF_vector.h:209
vector< elem_t > type
element type
Definition: SF_container.h:406
Classes similar to unordered_set and unordered_map, but with better performance.
The overlapping_layout class contains the algorithms related to managing overlapping parallel index s...
Definition: SF_container.h:197
void dsp_from_cnt(const vector< T > &cnt, vector< T > &dsp)
Compute displacements from counts.
Definition: SF_vector.h:310
void globalize(SF_nbr nbr_type)
Localize the connectivity data w.r.t. a given numbering.
Definition: SF_container.h:513
double mag(const Point &vect)
vector magnitude
Definition: SF_container.h:111