dune-grid  2.2.1
alugrid/3d/indexsets.hh
Go to the documentation of this file.
1 #ifndef DUNE_ALU3DGRIDINDEXSETS_HH
2 #define DUNE_ALU3DGRIDINDEXSETS_HH
3 
4 //- System includes
5 #include <vector>
6 
7 //- Dune includes
8 #include <dune/common/stdstreams.hh>
9 #include <dune/common/bigunsignedint.hh>
10 
11 #include <dune/grid/common/grid.hh>
13 
14 
15 //- Local includes
16 #include "alu3dinclude.hh"
17 #include "topology.hh"
18 #include "alu3diterators.hh"
19 
20 namespace Dune
21 {
22 
23  // External Forward Declarations
24  // -----------------------------
25 
26  template< ALU3dGridElementType, class >
27  class ALU3dGrid;
28 
29  template<int cd, int dim, class GridImp>
30  class ALU3dGridEntity;
31 
32 
33 
34  // ALU3dGridHierarchicIndexSet
35  // ---------------------------
36 
38  template< ALU3dGridElementType elType, class Comm >
40  : public IndexSet< ALU3dGrid< elType, Comm >, ALU3dGridHierarchicIndexSet< elType, Comm > >
41  {
43 
45  enum { numCodim = GridType::dimension + 1 };
46 
47  friend class ALU3dGrid< elType, Comm >;
48 
49  // constructor
51  : grid_( grid )
52  {}
53 
54  public:
55  typedef typename GridType::Traits::template Codim<0>::Entity EntityCodim0Type;
56 
58  template <class EntityType>
59  int index (const EntityType & ep) const
60  {
61  enum { cd = EntityType :: codimension };
62  return index<cd>(ep);
63  }
64 
66  template< int codim >
67  int index ( const typename GridType::Traits::template Codim< codim >::Entity &entity ) const
68  {
69  return GridType::getRealImplementation( entity ).getIndex();
70  }
71 
73  int subIndex ( const EntityCodim0Type &e, int i, unsigned int codim ) const
74  {
75  // call method subIndex on real implementation
76  return GridType::getRealImplementation( e ).subIndex( i, codim );
77  }
78 
81  int size ( GeometryType type ) const
82  {
83  if( elType == tetra && !type.isSimplex() ) return 0;
84  if( elType == hexa && !type.isCube() ) return 0;
85  // return size of hierarchic index set
86  return this->size(GridType::dimension-type.dim());
87  }
88 
90  int size ( int codim ) const
91  {
92  // return size of hierarchic index set
93  return grid_.hierSetSize(codim);
94  }
95 
97  const std::vector<GeometryType>& geomTypes (int codim) const
98  {
99  return grid_.geomTypes(codim);
100  }
101 
103  template <class EntityType>
104  bool contains (const EntityType &) const { return true; }
105 
106  private:
107  // our Grid
108  const GridType & grid_;
109  };
110 
115 
116  class ALUMacroKey : public ALU3DSPACE Key4<int>
117  {
118  typedef int A;
119  typedef ALUMacroKey ThisType;
120  typedef ALU3DSPACE Key4<A> BaseType;
121 
122  public:
123  ALUMacroKey() : BaseType(-1,-1,-1,-1) {}
124  ALUMacroKey(const A&a,const A&b,const A&c,const A&d) : BaseType(a,b,c,d) {}
125  ALUMacroKey(const ALUMacroKey & org ) : BaseType(org) {}
127  {
129  return *this;
130  }
131 
132  bool operator == (const ALUMacroKey & org) const
133  {
134  return ( (this->_a == org._a) &&
135  (this->_b == org._b) &&
136  (this->_c == org._c) &&
137  (this->_d == org._d) );
138  }
139 
140  // operator < is already implemented in BaseType
141  bool operator > (const ALUMacroKey & org) const
142  {
143  return ( (!this->operator == (org)) && (!this->operator <(org)) );
144  }
145 
146  void print(std::ostream & out) const
147  {
148  out << "[" << this->_a << "," << this->_b << "," << this->_c << "," << this->_d << "]";
149  }
150  };
151 
152  template <class MacroKeyImp>
153  class ALUGridId
154  {
155  MacroKeyImp key_;
156  int nChild_;
157  int codim_;
158  public:
159  ALUGridId() : key_()
160  , nChild_(-1)
161  , codim_(-1)
162  {}
163 
164  ALUGridId(const MacroKeyImp & key, int nChild , int cd)
165  : key_(key) , nChild_(nChild)
166  , codim_(cd)
167  {}
168 
169  ALUGridId(const ALUGridId & org )
170  : key_(org.key_)
171  , nChild_(org.nChild_)
172  , codim_(org.codim_)
173  {}
174 
175  ALUGridId & operator = (const ALUGridId & org )
176  {
177  key_ = org.key_;
178  nChild_ = org.nChild_;
179  codim_ = org.codim_;
180  return *this;
181  }
182 
183  bool operator == (const ALUGridId & org) const
184  {
185  return equals(org);
186  }
187 
188  bool operator != (const ALUGridId & org) const
189  {
190  return ! equals(org);
191  }
192 
193  bool operator <= (const ALUGridId & org) const
194  {
195  if(equals(org)) return true;
196  else return lesser(org);
197  }
198 
199  bool operator >= (const ALUGridId & org) const
200  {
201  if(equals(org)) return true;
202  else return ! lesser(org);
203  }
204 
205  bool operator < (const ALUGridId & org) const
206  {
207  return lesser(org);
208  }
209 
210  bool operator > (const ALUGridId & org) const
211  {
212  return (!equals(org) && ! lesser(org));
213  }
214 
215  const MacroKeyImp & getKey() const { return key_; }
216  int nChild() const { return nChild_; }
217  int codim() const { return codim_; }
218 
219  bool isValid () const
220  {
221  return ( (nChild_ >= 0) && (codim_ >= 0) );
222  }
223 
224  void reset()
225  {
226  nChild_ = -1;
227  codim_ = -1;
228  }
229 
230  void print(std::ostream & out) const
231  {
232  out << "(" << getKey() << "," << nChild_ << "," << codim_ << ")";
233  }
234 
235  protected:
236  // returns true is the id is lesser then org
237  bool lesser(const ALUGridId & org) const
238  {
239  if(getKey() < org.getKey() ) return true;
240  if(getKey() > org.getKey() ) return false;
241  if(getKey() == org.getKey() )
242  {
243  if(nChild_ == org.nChild_)
244  {
245  return codim_ < org.codim_;
246  }
247  else
248  return nChild_ < org.nChild_;
249  }
250  assert( equals(org) );
251  return false;
252  }
253 
254  // returns true if this id equals org
255  bool equals(const ALUGridId & org) const
256  {
257  return ( (getKey() == org.getKey() ) && (nChild_ == org.nChild_)
258  && (codim_ == org.codim_) );
259  }
260  };
261 
262  inline std::ostream& operator<< (std::ostream& s, const ALUMacroKey & key)
263  {
264  key.print(s);
265  return s;
266  }
267 
268  template <class KeyImp>
269  inline std::ostream& operator<< (std::ostream& s, const ALUGridId<KeyImp> & id)
270  {
271  id.print(s);
272  return s;
273  }
274 
275  //*****************************************************************
276  //
277  // --GlobalIdSet
278  //
279  //*****************************************************************
281  template< ALU3dGridElementType elType, class Comm >
283  : public IdSet< ALU3dGrid< elType, Comm >, ALU3dGridGlobalIdSet< elType, Comm > ,
284  typename ALU3dGrid< elType, Comm >::Traits::GlobalIdType >,
285  public ALU3DSPACE AdaptRestrictProlongType
286  {
289 
290  typedef ALU3dImplTraits< elType, Comm > ImplTraitsType;
291  typedef typename ImplTraitsType::IMPLElementType IMPLElementType;
292  typedef typename ImplTraitsType::GEOElementType GEOElementType;
293  typedef typename ImplTraitsType::GEOFaceType GEOFaceType;
294  typedef typename ImplTraitsType::GEOEdgeType GEOEdgeType;
295 
296  typedef typename ImplTraitsType::GitterImplType GitterImplType;
297 
298  typedef typename ImplTraitsType::HElementType HElementType;
299  typedef typename ImplTraitsType::HFaceType HFaceType;
300  typedef typename ImplTraitsType::HEdgeType HEdgeType;
301  typedef typename ImplTraitsType::VertexType VertexType;
302  typedef typename ImplTraitsType::HBndSegType HBndSegType;
303 
305 
306  public:
309 
310  private:
311  typedef ALUMacroKey MacroKeyType;
312 
313  typedef ALUGridId < MacroKeyType > MacroIdType; // same as IdType
314  enum { numCodim = GridType::dimension+1 };
315 
316  // this means that only up to 300000000 entities are allowed
317  typedef typename GridType::Traits::template Codim<0>::Entity EntityCodim0Type;
318  private:
319  mutable std::map< int , IdType > ids_[numCodim];
320  //mutable std::map< int , MacroKeyType > macroKeys_[numCodim];
321 
322  // our Grid
323  const GridType & grid_;
324 
325  // the hierarchicIndexSet
326  const HierarchicIndexSetType & hset_;
327 
328  int vertexKey_[4];
329 
330  int chunkSize_ ;
331 
332  enum { startOffSet_ = 0 };
333 
334  public:
335 
338  using IdSet < GridType , ALU3dGridGlobalIdSet, IdType > :: subId;
339 
342  : grid_(grid), hset_(grid.hierarchicIndexSet())
343  , chunkSize_(100)
344  {
345  if(elType == hexa)
346  {
347  // see ALUGrid/src/serial/gitter_mgb.cc
348  // InsertUniqueHexa
349  const int vxKey[4] = {0,1,3,4};
350  for(int i=0; i<4; i++) vertexKey_[i] = vxKey[i];
351  }
352  else
353  {
354  assert( elType == tetra );
355  // see ALUGrid/src/serial/gitter_mgb.cc
356  // InsertUniqueTetra
357  const int vxKey[4] = {0,1,2,3};
358  for(int i=0; i<4; i++) vertexKey_[i] = vxKey[i];
359  }
360 
361  // setup the id set
362  buildIdSet();
363  }
364 
366 
367  // update id set after adaptation
368  void updateIdSet()
369  {
370  // to be revised
371  buildIdSet();
372  }
373 
374  // print all ids
375  void print () const
376  {
377  for(int i=0 ;i<numCodim; ++i)
378  {
379  std::cout << "*****************************************************\n";
380  std::cout << "Ids for codim " << i << "\n";
381  std::cout << "*****************************************************\n";
382  for(unsigned int k=0; k<ids_[i].size(); ++k)
383  {
384  std::cout << "Item[" << i << "," << k <<"] has id " << ids_[i][k] << "\n";
385  }
386  std::cout << "\n\n\n";
387  }
388  }
389 
390  template <class IterType>
391  void checkId(const IdType & macroId, const IterType & idIter) const //int codim , unsigned int num ) const
392  {
393 
394  IdType id = getId(macroId);
395  for(int i=0 ;i<numCodim; ++i)
396  {
397  typedef typename std::map<int,IdType>::iterator IteratorType;
398  IteratorType end = ids_[i].end();
399  for(IteratorType it = ids_[i].begin(); it != end; ++it)
400  //for(unsigned int k=0; k<ids_[i].size(); ++k)
401  {
402  if(idIter == it) continue;
403  //if((i == codim) && (k == num)) continue;
404  const IdType & checkMId = (*it).second; //ids_[i][k];
405  IdType checkId = getId(checkMId);
406  if( id == checkId )
407  {
408  //std::cout << "Check(codim,num = " << codim<< "," << num <<") failed for k="<<k << " codim = " << i << "\n";
409  std::cout << id << " equals " << checkId << "\n";
410  assert( id != checkId );
411  DUNE_THROW(GridError," " << id << " equals " << checkId << "\n");
412  }
413  else
414  {
415  bool lesser = (id < checkId);
416  bool greater = (id > checkId);
417  assert( lesser != greater );
418  if( lesser == greater )
419  {
420  assert( lesser != greater );
421  DUNE_THROW(GridError," lesser equals greater of one id ");
422  }
423  }
424  }
425  }
426  }
427 
428  // check id set for uniqueness
429  void uniquenessCheck() const
430  {
431  for(int i=0 ;i<numCodim; i++)
432  {
433  typedef typename std::map<int,IdType>::iterator IteratorType;
434  IteratorType end = ids_[i].end();
435  for(IteratorType it = ids_[i].begin(); it != end; ++it)
436  //unsigned int k=0; k<ids_[i].size(); ++k)
437  {
438  const IdType & id = (*it).second; //ids_[i][k];
439  if( id.isValid() )
440  checkId(id,it);//i,k);
441  }
442  }
443  }
444 
445  void setChunkSize( int chunkSize )
446  {
447  chunkSize_ = chunkSize;
448  }
449 
450  // creates the id set
451  void buildIdSet ()
452  {
453  for(int i=0; i<numCodim; ++i)
454  {
455  ids_[i].clear();
456  }
457 
458  GitterImplType &gitter = grid_.myGrid();
459 
460  // all interior and border vertices
461  {
462  typename ALU3DSPACE AccessIterator< VertexType >::Handle fw( gitter.container() );
463  for( fw.first (); !fw.done(); fw.next() )
464  {
465  int idx = fw.item().getIndex();
466  ids_[3][idx] = buildMacroVertexId( fw.item() );
467  }
468  }
469 
470  // all ghost vertices
471  {
472  typedef typename ALU3DSPACE ALU3dGridLevelIteratorWrapper< 3, Ghost_Partition, Comm > IteratorType;
473  IteratorType fw (grid_ , 0 , grid_.nlinks() );
474  typedef typename IteratorType :: val_t val_t;
475  for (fw.first () ; ! fw.done () ; fw.next ())
476  {
477  val_t & item = fw.item();
478  assert( item.first );
479  VertexType & vx = * (item.first);
480  int idx = vx.getIndex();
481  ids_[3][idx] = buildMacroVertexId( vx );
482  }
483  }
484 
485  // create ids for all macro edges
486  {
487  typename ALU3DSPACE AccessIterator< HEdgeType >::Handle w( gitter.container() );
488  for (w.first(); !w.done(); w.next())
489  {
490  int idx = w.item().getIndex();
491  ids_[2][idx] = buildMacroEdgeId( w.item() );
492  buildEdgeIds( w.item() , ids_[2][idx] , startOffSet_ );
493  }
494  }
495 
496  // all ghost edges
497  {
498  typedef typename ALU3DSPACE ALU3dGridLevelIteratorWrapper< 2, Ghost_Partition, Comm > IteratorType;
499  IteratorType fw( grid_, 0, grid_.nlinks() );
500  typedef typename IteratorType :: val_t val_t;
501  for (fw.first () ; ! fw.done () ; fw.next ())
502  {
503  val_t & item = fw.item();
504  assert( item.first );
505  HEdgeType & edge = * (item.first);
506  int idx = edge.getIndex();
507 
508  ids_[2][idx] = buildMacroEdgeId( edge );
509  buildEdgeIds( edge , ids_[2][idx] , startOffSet_ );
510  }
511  }
512 
513 
514  // for all macro faces and all children
515  {
516  typename ALU3DSPACE AccessIterator< HFaceType >::Handle w( gitter.container() );
517  for (w.first () ; ! w.done () ; w.next ())
518  {
519  int idx = w.item().getIndex();
520  ids_[1][idx] = buildMacroFaceId( w.item() );
521  buildFaceIds( w.item() , ids_[1][idx] , startOffSet_ );
522  }
523  }
524 
525  // all ghost faces
526  {
527  typedef typename ALU3DSPACE ALU3dGridLevelIteratorWrapper< 1, Ghost_Partition, Comm > IteratorType;
528  IteratorType fw (grid_ , 0 , grid_.nlinks() );
529  typedef typename IteratorType :: val_t val_t;
530  for (fw.first () ; ! fw.done () ; fw.next ())
531  {
532  val_t & item = fw.item();
533  assert( item.first );
534  HFaceType & face = * (item.first);
535  int idx = face.getIndex();
536  ids_[1][idx] = buildMacroFaceId( face );
537  buildFaceIds( face , ids_[1][idx] , startOffSet_ );
538  }
539  }
540 
541  // for all macro elements and all internal entities
542  {
543  typename ALU3DSPACE AccessIterator< HElementType >::Handle w( gitter.container() );
544  for (w.first () ; ! w.done () ; w.next ())
545  {
546  int idx = w.item().getIndex();
547  ids_[0][idx] = buildMacroElementId( w.item() );
548  buildElementIds( w.item() , ids_[0][idx] , startOffSet_ );
549  }
550  }
551 
552  // all ghost elements
553  {
554  typedef typename ALU3DSPACE ALU3dGridLevelIteratorWrapper< 0, Ghost_Partition, Comm > IteratorType;
555  IteratorType fw (grid_ , 0 , grid_.nlinks() );
556  typedef typename IteratorType :: val_t val_t;
557  for (fw.first () ; ! fw.done () ; fw.next ())
558  {
559  val_t & item = fw.item();
560  assert( item.second );
561  HElementType & elem = * ( item.second->getGhost().first );
562  int idx = elem.getIndex();
563  ids_[0][idx] = buildMacroElementId( elem );
564  buildElementIds( elem , ids_[0][idx] , startOffSet_ );
565  }
566  }
567 
568  // check uniqueness of id only in serial, because
569  // in parallel some faces and edges of ghost exists more than once
570  // but have the same id, but not the same index, there for the check
571  // will fail for ghost elements
572 #if ! ALU3DGRID_PARALLEL
573  // be carefull with this check, it's complexity is O(N^2)
574  //uniquenessCheck();
575 #endif
576  }
577 
578  IdType buildMacroVertexId(const VertexType & item )
579  {
580  int vx[4] = { item.ident(), -1, -1, -1};
581  enum {codim = 3 };
582  MacroKeyType key(vx[0],vx[1],vx[2],vx[3]);
583  MacroIdType id(key,1, codim + startOffSet_ );
584  return id;
585  }
586 
587  IdType buildMacroEdgeId(const HEdgeType & item )
588  {
589  const GEOEdgeType & edge = static_cast<const GEOEdgeType &> (item);
590  int vx[4] = {-1,-1,-1,-1};
591  for(int i=0; i<2; ++i)
592  {
593  vx[i] = edge.myvertex(i)->ident();
594  }
595 
596  enum { codim = 2 };
597  MacroKeyType key(vx[0],vx[1],vx[2],vx[3]);
598  MacroIdType id( key,1, codim + startOffSet_ );
599  return id;
600  }
601 
602  IdType buildMacroFaceId(const HFaceType & item )
603  {
604  const GEOFaceType & face = static_cast<const GEOFaceType &> (item);
605  int vx[4] = {-1,-1,-1,-1};
606  for(int i=0; i<3; ++i)
607  {
608  vx[i] = face.myvertex(i)->ident();
609  }
610 
611  enum { codim = 1 };
612  MacroKeyType key(vx[0],vx[1],vx[2],vx[3]);
613  MacroIdType id(key,1, codim + startOffSet_ );
614  return id;
615  }
616 
617  IdType buildMacroElementId(const HElementType & item )
618  {
619  const GEOElementType & elem = static_cast<const GEOElementType &> (item);
620  int vx[4] = {-1,-1,-1,-1};
621  for(int i=0; i<4; ++i)
622  {
623  vx[i] = elem.myvertex(vertexKey_[i])->ident();
624  }
625  enum { codim = 0 };
626  MacroKeyType key(vx[0],vx[1],vx[2],vx[3]);
627  return MacroIdType(key,1, codim + startOffSet_ );
628  }
629 
630  template <int cd>
631  IdType createId(const typename ImplTraitsType::
632  template Codim<cd>::InterfaceType & item , const IdType & creatorId , int nChild )
633  {
634  assert( creatorId.isValid() );
635 
636  // we have up to 12 internal hexa faces, therefore need 100 offset
637  enum { childOffSet = ((cd == 1) && (elType == hexa)) ? 16 : 8 };
638  enum { codimOffSet = 4 };
639 
640  assert( nChild < childOffSet );
641 
642  int newChild = (creatorId.nChild() * childOffSet ) + nChild;
643  int newCodim = (creatorId.codim() * codimOffSet ) + ( cd + startOffSet_ );
644 
645  IdType newId( creatorId.getKey() , newChild , newCodim );
646  assert( newId != creatorId );
647  return newId;
648  }
649 
650  // build ids for all children of this element
651  void buildElementIds(const HElementType & item , const IdType & macroId , int nChild)
652  {
653  enum { codim = 0 };
654  ids_[codim][item.getIndex()] = createId<codim>(item,macroId,nChild);
655 
656  const IdType & itemId = ids_[codim][item.getIndex()];
657 
658  buildInteriorElementIds(item,itemId);
659  }
660 
661  // build ids for all children of this element
662  void buildInteriorElementIds(const HElementType & item , const IdType & fatherId)
663  {
664  assert( fatherId.isValid() );
665 
666  // build id for inner vertex
667  {
668  const VertexType * v = item.innerVertex() ;
669  // for tetras there is no inner vertex, therefore check
670  if(v) buildVertexIds(*v,fatherId );
671  }
672 
673  // build edge ids for all inner edges
674  {
675  int inneredge = startOffSet_;
676  for(const HEdgeType * e = item.innerHedge () ; e ; e = e->next ())
677  {
678  buildEdgeIds(*e,fatherId,inneredge);
679  ++inneredge;
680  }
681  }
682 
683  // build face ids for all inner faces
684  {
685  int innerface = startOffSet_;
686  for(const HFaceType * f = item.innerHface () ; f ; f = f->next ())
687  {
688  buildFaceIds(*f,fatherId,innerface);
689  ++innerface;
690  }
691  }
692 
693  // build ids of all children
694  {
695  int numChild = startOffSet_;
696  for(const HElementType * child = item.down(); child; child =child->next() )
697  {
698  //assert( numChild == child->nChild() );
699  buildElementIds(*child, fatherId, numChild);
700  ++numChild;
701  }
702  }
703  }
704 
705  // build ids for all children of this face
706  void buildFaceIds(const HFaceType & face, const IdType & fatherId , int innerFace )
707  {
708  enum { codim = 1 };
709  ids_[codim][face.getIndex()] = createId<codim>(face,fatherId,innerFace);
710  const IdType & faceId = ids_[codim][face.getIndex()];
711 
712  buildInteriorFaceIds(face,faceId);
713  }
714 
715  // build ids for all children of this face
716  void buildInteriorFaceIds(const HFaceType & face, const IdType & faceId)
717  {
718  assert( faceId.isValid () );
719 
720  // build id for inner vertex
721  {
722  const VertexType * v = face.innerVertex() ;
723  //std::cout << "create inner vertex of face " << face.getIndex() << "\n";
724  if(v) buildVertexIds(*v,faceId );
725  }
726 
727  // build ids for all inner edges
728  {
729  int inneredge = startOffSet_;
730  for (const HEdgeType * e = face.innerHedge () ; e ; e = e->next ())
731  {
732  buildEdgeIds(*e,faceId ,inneredge );
733  ++inneredge;
734  }
735  }
736 
737  // build ids for all child faces
738  {
739  int child = startOffSet_;
740  for(const HFaceType * f = face.down () ; f ; f = f->next ())
741  {
742  assert( child == f->nChild()+startOffSet_);
743  buildFaceIds(*f,faceId,child);
744  ++child;
745  }
746  }
747  }
748 
749  // build ids for all children of this edge
750  void buildEdgeIds(const HEdgeType & edge, const IdType & fatherId , int inneredge)
751  {
752  enum { codim = 2 };
753  ids_[codim][edge.getIndex()] = createId<codim>(edge,fatherId,inneredge);
754  const IdType & edgeId = ids_[codim][edge.getIndex()];
755  buildInteriorEdgeIds(edge,edgeId);
756  }
757 
758  void buildInteriorEdgeIds(const HEdgeType & edge, const IdType & edgeId)
759  {
760  assert( edgeId.isValid() );
761 
762  // build id for inner vertex
763  {
764  const VertexType * v = edge.innerVertex() ;
765  if(v) buildVertexIds(*v,edgeId );
766  }
767 
768  // build ids for all inner edges
769  {
770  int child = startOffSet_;
771  for (const HEdgeType * e = edge.down () ; e ; e = e->next ())
772  {
773  assert( child == e->nChild()+ startOffSet_ );
774  buildEdgeIds(*e,edgeId , child );
775  ++child;
776  }
777  }
778  }
779 
780  // build id for this vertex
781  void buildVertexIds(const VertexType & vertex, const IdType & fatherId )
782  {
783  enum { codim = 3 };
784  // inner vertex number is 1
785  ids_[codim][vertex.getIndex()] = createId<codim>(vertex,fatherId,1);
786  assert( ids_[codim][vertex.getIndex()].isValid() );
787  }
788 
789  friend class ALU3dGrid< elType, Comm >;
790 
791  const IdType & getId(const IdType & macroId) const
792  {
793  return macroId;
794  }
795 
796  public:
798  template <class EntityType>
799  IdType id (const EntityType & ep) const
800  {
801  enum { cd = EntityType :: codimension };
802  assert( ids_[cd].find( hset_.index(ep) ) != ids_[cd].end() );
803  const IdType & macroId = ids_[cd][hset_.index(ep)];
804  assert( macroId.isValid() );
805  return getId(macroId);
806  }
807 
809  template <int codim>
810  IdType id (const typename GridType:: template Codim<codim> :: Entity & ep) const
811  {
812  assert( ids_[codim].find( hset_.index(ep) ) != ids_[codim].end() );
813  const IdType & macroId = ids_[codim][hset_.index(ep)];
814  assert( macroId.isValid() );
815  return getId(macroId);
816  }
817 
819  IdType subId ( const EntityCodim0Type &e, int i, unsigned int codim ) const
820  {
821  const int hIndex = hset_.subIndex( e, i, codim );
822  assert( ids_[ codim ].find( hIndex ) != ids_[ codim ].end() );
823  const IdType &macroId = ids_[ codim ][ hIndex ];
824  assert( macroId.isValid() );
825  return getId( macroId );
826  }
827 
828  template <int d, ALU3dGridElementType element_t >
829  struct BuildIds;
830 
831  template <int d>
832  struct BuildIds<d,tetra>
833  {
834  //static const IdType zero;
835  template <class MyIdSet, class IdStorageType>
836  static void buildFace(MyIdSet & set, const HElementType & item, int faceNum,
837  IdStorageType & ids )
838  {
839  const IMPLElementType & elem = static_cast<const IMPLElementType &> (item);
840  const HFaceType & face = *(elem.myhface3(faceNum));
841  const IdType & id = ids[face.getIndex()];
842  assert( id.isValid() );
843  set.buildInteriorFaceIds(face,id);
844  }
845  };
846 
847  template <int d>
848  struct BuildIds<d,hexa>
849  {
850  //static const IdType zero;
851  template <class MyIdSet, class IdStorageType>
852  static void buildFace(MyIdSet & set, const HElementType & item, int faceNum,
853  IdStorageType & ids )
854  {
855  const IMPLElementType & elem = static_cast<const IMPLElementType &> (item);
856  const HFaceType & face = *(elem.myhface4(faceNum));
857  const IdType & id = ids[face.getIndex()];
858  assert( id.isValid() );
859  set.buildInteriorFaceIds(face,id);
860  }
861  };
862 
863  // create ids for refined elements
864  int postRefinement( HElementType & item )
865  {
866  {
867  enum { elCodim = 0 };
868  const IdType & fatherId = ids_[elCodim][item.getIndex()];
869  assert( fatherId.isValid() );
870  buildInteriorElementIds(item, fatherId );
871  }
872 
873  for(int i=0; i<EntityCountType::numFaces; ++i)
874  {
875  enum { faceCodim = 1 };
876  BuildIds< GridType::dimension, elType >::buildFace(*this,item,i,ids_[faceCodim]);
877  }
878 
879  for(int i=0; i<EntityCountType::numEdges; ++i)
880  {
881  enum { edgeCodim = 2 };
882  const IMPLElementType & elem = static_cast<const IMPLElementType &> (item);
883  const HEdgeType & edge = *( elem.myhedge1(i));
884  const IdType & id = ids_[edgeCodim][edge.getIndex()];
885  assert( id.isValid() );
886  buildInteriorEdgeIds(edge,id);
887  }
888  return 0;
889  }
890 
891  // dummy functions
892  int preCoarsening( HElementType & elem )
893  {
894  /*
895  const IdType & fatherId = ids_[0][item.getIndex()];
896 
897  removeElementIds(item,fatherId,item.nChild());
898 
899  for(int i=0; i<EntityCountType::numFaces; ++i)
900  BuildIds<dim,elType>::buildFace(*this,item,i,ids_[1]);
901 
902  for(int i=0; i<EntityCountType::numEdges; ++i)
903  {
904  const IMPLElementType & elem = static_cast<const IMPLElementType &> (item);
905  const HEdgeType & edge = *( elem.myhedge1(i));
906  const HEdgeType * child = edge.down();
907  assert( child );
908  if( ids_[2][child->getIndex() ] > zero_ ) continue;
909  buildEdgeIds(edge,ids_[2][edge.getIndex()],0);
910  }
911 #ifndef NDEBUG
912  //uniquenessCheck();
913 #endif
914  */
915  return 0;
916  }
917 
918  // dummy functions
919  int preCoarsening ( HBndSegType & el ) { return 0; }
920 
922  int postRefinement ( HBndSegType & el ) { return 0; }
923 
924  };
925 
926  //***********************************************************
927  //
928  // --LocalIdSet
929  //
930  //***********************************************************
931 
933  template< ALU3dGridElementType elType, class Comm >
935  : public IdSet< ALU3dGrid< elType, Comm >, ALU3dGridLocalIdSet< elType, Comm >, int >,
936  public ALU3DSPACE AdaptRestrictProlongType
937  {
939 
940  typedef ALU3dImplTraits< elType, Comm > ImplTraitsType;
941  typedef typename ImplTraitsType::HElementType HElementType;
942  typedef typename ImplTraitsType::HBndSegType HBndSegType;
943 
946 
947  // this means that only up to 300000000 entities are allowed
948  enum { codimMultiplier = 300000000 };
949  typedef typename GridType::Traits::template Codim<0>::Entity EntityCodim0Type;
950 
951  // create local id set , only for the grid allowed
952  ALU3dGridLocalIdSet(const GridType & grid) : hset_(grid.hierarchicIndexSet())
953  {
954  for( int codim = 0; codim <= GridType::dimension; ++codim )
955  codimStart_[ codim ] = codim * codimMultiplier;
956  }
957 
958  friend class ALU3dGrid< elType, Comm >;
959 
960  // fake method to have the same method like GlobalIdSet
961  void updateIdSet() {}
962 
963  public:
965  typedef int IdType;
966 
970 
972  template <class EntityType>
973  int id (const EntityType & ep) const
974  {
975  enum { cd = EntityType :: codimension };
976  assert( hset_.size(cd) < codimMultiplier );
977  return codimStart_[cd] + hset_.index(ep);
978  }
979 
981  template <int codim>
982  int id (const typename GridType:: template Codim<codim> :: Entity & ep) const
983  {
984  //enum { cd = EntityType :: codimension };
985  assert( hset_.size(codim) < codimMultiplier );
986  return codimStart_[codim] + hset_.index(ep);
987  }
988 
990  IdType subId ( const EntityCodim0Type &e, int i, unsigned int codim ) const
991  {
992  assert( hset_.size( codim ) < codimMultiplier );
993  return codimStart_[ codim ] + hset_.subIndex( e, i, codim );
994  }
995 
996  // dummy functions
997  int preCoarsening( HElementType & elem ) { return 0; }
998  // create ids for refined elements
999  int postRefinement( HElementType & item ) { return 0; }
1000 
1001  // dummy functions
1002  int preCoarsening ( HBndSegType & el ) { return 0; }
1003 
1005  int postRefinement ( HBndSegType & el ) { return 0; }
1006 
1007  void setChunkSize( int chunkSize ) {}
1008 
1009  private:
1010  // our HierarchicIndexSet
1011  const HierarchicIndexSetType & hset_;
1012 
1013  // store start of each codim numbers
1014  int codimStart_[ GridType::dimension+1 ];
1015  };
1016 
1017 } // end namespace Dune
1018 
1019 #endif // #ifndef DUNE_ALU3DGRIDINDEXSETS_HH