1#ifndef DUNE_MULTIDOMAINGRID_SUBDOMAINGRID_HH
2#define DUNE_MULTIDOMAINGRID_SUBDOMAINGRID_HH
7#include <dune/common/exceptions.hh>
9#include <dune/grid/multidomaingrid/hostgridaccessor.hh>
10#include <dune/grid/multidomaingrid/subdomainset.hh>
12#include <dune/grid/multidomaingrid/subdomaingrid/geometry.hh>
13#include <dune/grid/multidomaingrid/subdomaingrid/localgeometry.hh>
14#include <dune/grid/multidomaingrid/subdomaingrid/entity.hh>
15#include <dune/grid/multidomaingrid/subdomaingrid/iterator.hh>
16#include <dune/grid/multidomaingrid/subdomaingrid/hierarchiciterator.hh>
17#include <dune/grid/multidomaingrid/subdomaingrid/intersection.hh>
18#include <dune/grid/multidomaingrid/subdomaingrid/intersectioniterator.hh>
19#include <dune/grid/multidomaingrid/subdomaingrid/idsets.hh>
20#include <dune/grid/multidomaingrid/subdomaingrid/indexsets.hh>
21#include <dune/grid/multidomaingrid/subdomaingrid/gridview.hh>
30template<
typename,
typename>
35template<
typename MDGr
id>
38template<
typename MDGr
id>
39struct SubDomainGridFamily {
43 static const int dim = MDGrid::dimension;
44 static const int dimw = MDGrid::dimensionworld;
51 using Grid = SubDomainGrid<MDGrid>;
54 using LeafIntersection = Dune::Intersection<
60 typename MDGrid::LeafIndexSetImp
62 typename MDGrid::LeafGridView::Intersection
66 using LevelIntersection = Dune::Intersection<
72 typename MDGrid::LevelIndexSetImp
74 typename MDGrid::LevelGridView::Intersection
78 using LeafIntersectionIterator = Dune::IntersectionIterator<
80 IntersectionIteratorWrapper<
84 typename MDGrid::LeafIndexSetImp
86 typename MDGrid::LeafGridView::IntersectionIterator
92 typename MDGrid::LeafIndexSetImp
94 typename MDGrid::LeafGridView::Intersection
98 using LevelIntersectionIterator = Dune::IntersectionIterator<
100 IntersectionIteratorWrapper<
104 typename MDGrid::LevelIndexSetImp
106 typename MDGrid::LevelGridView::IntersectionIterator
112 typename MDGrid::LevelIndexSetImp
114 typename MDGrid::LevelGridView::Intersection
118 using HierarchicIterator = Dune::EntityIterator< 0, const Grid, HierarchicIteratorWrapper< const Grid > >;
120 using LevelGridView = Dune::GridView<LevelGridViewTraits<const Grid>>;
121 using LeafGridView = Dune::GridView<LeafGridViewTraits<const Grid>>;
127 using Geometry = Dune::Geometry<dim-cd, dimw,
const Grid, GeometryWrapper>;
128 using LocalGeometry = Dune::Geometry<dim-cd, dim,
const Grid, LocalGeometryWrapper>;
130 using Entity = Dune::Entity<cd, dim, const Grid, EntityWrapper>;
132 using EntitySeed = EntitySeedWrapper<typename MDGrid::HostGrid::template Codim<cd>::EntitySeed>;
134 template <PartitionIteratorType pitype>
138 using LevelIterator = Dune::EntityIterator<
142 typename Traits::LevelGridView,
143 typename MDGrid::LevelGridView::template Codim<cd>::template Partition<pitype>::Iterator,
150 using LeafIterator = Dune::EntityIterator<
154 typename Traits::LeafGridView,
155 typename MDGrid::LeafGridView::template Codim<cd>::template Partition<pitype>::Iterator,
163 using LeafIterator =
typename Partition< All_Partition >::LeafIterator;
164 using LevelIterator =
typename Partition< All_Partition >::LevelIterator;
167 friend class Dune::Entity<cd, dim, const Grid, EntityWrapper>;
171 using LevelIndexSet = IndexSetWrapper<const Grid, typename MDGrid::LevelIndexSetImp>;
172 using LeafIndexSet = IndexSetWrapper<const Grid, typename MDGrid::LeafIndexSetImp>;
174 using GlobalIdSet = IdSet<
178 typename MDGrid::HostGrid::Traits::GlobalIdSet
180 typename MDGrid::HostGrid::Traits::GlobalIdSet::IdType
183 using LocalIdSet = IdSet<
187 typename MDGrid::HostGrid::Traits::LocalIdSet
189 typename MDGrid::HostGrid::Traits::LocalIdSet::IdType
192 using Communication =
typename MDGrid::Communication;
198template<
typename MDGr
id>
200 public GridDefaultImplementation<MDGrid::dimension,
201 MDGrid::dimensionworld,
202 typename MDGrid::ctype,
203 SubDomainGridFamily<MDGrid> > {
205 template<
typename,
typename>
206 friend class ::Dune::mdgrid::MultiDomainGrid;
208 template<
int codim,
int dim,
typename Gr
idImp>
209 friend class EntityWrapperBase;
211 template<
int codim,
int dim,
typename Gr
idImp>
212 friend class EntityWrapper;
214 template<
typename,
typename,
int codim, PartitionIteratorType pitype,
typename Gr
idImp>
215 friend class IteratorWrapper;
217 template<
typename Gr
idImp>
218 friend class HierarchicIteratorWrapper;
220 template<
int mydim,
int coorddim,
typename Gr
idImp>
221 friend class GeometryWrapper;
223 template<
int mydim,
int coorddim,
typename Gr
idImp>
224 friend class LocalGeometryWrapper;
226 template<
typename Gr
idImp,
typename WrappedIndexSet>
227 friend class IndexSetWrapper;
229 template<
typename Gr
idImp,
typename WrappedIdSet>
230 friend class IdSetWrapper;
232 template<
typename Gr
idImp>
233 friend struct ::Dune::mdgrid::detail::HostGridAccessor;
235 template<
typename,
typename,
typename>
236 friend class IntersectionIteratorWrapper;
238 template<
typename,
typename,
typename>
239 friend class IntersectionWrapper;
242 friend class LevelGridView;
245 friend class LeafGridView;
247 typedef GridDefaultImplementation<MDGrid::dimension,
248 MDGrid::dimensionworld,
249 typename MDGrid::ctype,
250 SubDomainGridFamily<MDGrid>
253 using GridImp = SubDomainGrid<MDGrid>;
257 using MultiDomainGrid = MDGrid;
259 using HostGrid =
typename MDGrid::HostGrid;
263 typedef IndexSetWrapper<const SubDomainGrid<MDGrid>,
typename MDGrid::LevelIndexSetImp> LevelIndexSetImp;
265 typedef IndexSetWrapper<const SubDomainGrid<MDGrid>,
typename MDGrid::LeafIndexSetImp> LeafIndexSetImp;
267 typedef IdSetWrapper<const SubDomainGrid<MDGrid>,
typename HostGrid::Traits::GlobalIdSet> GlobalIdSetImp;
269 typedef IdSetWrapper<const SubDomainGrid<MDGrid>,
typename HostGrid::Traits::LocalIdSet> LocalIdSetImp;
273 typedef SubDomainGridFamily<MDGrid> GridFamily;
274 typedef typename GridFamily::Traits Traits;
277 typedef typename MDGrid::ctype ctype;
280 typedef typename MDGrid::SubDomainIndex SubDomainIndex;
282 enum IntersectionType { neighbor, foreign, boundary, processor };
284 using BaseT::dimension;
285 using BaseT::dimensionworld;
290 template<
typename EntitySeed>
291 typename Traits::template Codim<EntitySeed::codimension>::Entity
292 entity(
const EntitySeed& entitySeed)
const
295 EntityWrapper<EntitySeed::codimension,dimension,const GridImp>(
297 typename MDGrid::template Codim<EntitySeed::codimension>::Entity(
298 _grid.entity(entitySeed)
303 int maxLevel()
const {
304 return _grid.maxLevel();
308 typename Traits::template Codim<codim>::LevelIterator lbegin(
int level)
const {
309 return IteratorWrapper<
310 typename Traits::LevelGridView,
311 typename MultiDomainGrid::LevelGridView::template Codim<codim>::template Partition<All_Partition>::Iterator,
316 &this->levelGridView(level).indexSet(),
317 _grid.levelGridView(level).template begin<codim>(),
318 _grid.levelGridView(level).template end<codim>()
323 typename Traits::template Codim<codim>::LevelIterator lend(
int level)
const {
324 return IteratorWrapper<
325 typename Traits::LevelGridView,
326 typename MultiDomainGrid::LevelGridView::template Codim<codim>::template Partition<All_Partition>::Iterator,
331 &this->levelGridView(level).indexSet(),
332 _grid.levelGridView(level).template end<codim>(),
333 _grid.levelGridView(level).template end<codim>()
337 template<
int codim, PartitionIteratorType pitype>
338 typename Traits::template Codim<codim>::template Partition<pitype>::LevelIterator lbegin(
int level)
const {
339 return IteratorWrapper<
340 typename Traits::LevelGridView,
341 typename MultiDomainGrid::LevelGridView::template Codim<codim>::template Partition<pitype>::Iterator,
346 &this->levelGridView(level).indexSet(),
347 _grid.levelGridView(level).template begin<codim,pitype>(),
348 _grid.levelGridView(level).template end<codim,pitype>()
352 template<
int codim, PartitionIteratorType pitype>
353 typename Traits::template Codim<codim>::template Partition<pitype>::LevelIterator lend(
int level)
const {
354 return IteratorWrapper<
355 typename Traits::LevelGridView,
356 typename MultiDomainGrid::LevelGridView::template Codim<codim>::template Partition<pitype>::Iterator,
361 &this->levelGridView(level).indexSet(),
362 _grid.levelGridView(level).template end<codim,pitype>(),
363 _grid.levelGridView(level).template end<codim,pitype>()
368 typename Traits::template Codim<codim>::LeafIterator leafbegin()
const {
369 return IteratorWrapper<
370 typename Traits::LeafGridView,
371 typename MultiDomainGrid::LeafGridView::template Codim<codim>::template Partition<All_Partition>::Iterator,
376 &this->leafGridView().indexSet(),
377 _grid.leafGridView().template begin<codim>(),
378 _grid.leafGridView().template end<codim>()
383 typename Traits::template Codim<codim>::LeafIterator leafend()
const {
384 return IteratorWrapper<
385 typename Traits::LeafGridView,
386 typename MultiDomainGrid::LeafGridView::template Codim<codim>::template Partition<All_Partition>::Iterator,
391 &this->leafGridView().indexSet(),
392 _grid.leafGridView().template end<codim>(),
393 _grid.leafGridView().template end<codim>()
397 template<
int codim, PartitionIteratorType pitype>
398 typename Traits::template Codim<codim>::template Partition<pitype>::LeafIterator leafbegin()
const {
399 return IteratorWrapper<
400 typename Traits::LeafGridView,
401 typename MultiDomainGrid::LeafGridView::template Codim<codim>::template Partition<pitype>::Iterator,
406 &this->leafGridView().indexSet(),
407 _grid.leafGridView().template begin<codim,pitype>(),
408 _grid.leafGridView().template end<codim,pitype>()
412 template<
int codim, PartitionIteratorType pitype>
413 typename Traits::template Codim<codim>::template Partition<pitype>::LeafIterator leafend()
const {
414 return IteratorWrapper<
415 typename Traits::LeafGridView,
416 typename MultiDomainGrid::LeafGridView::template Codim<codim>::template Partition<pitype>::Iterator,
421 &this->leafGridView().indexSet(),
422 _grid.leafGridView().template end<codim,pitype>(),
423 _grid.leafGridView().template end<codim,pitype>()
427 int size(
int level,
int codim)
const {
428 assert(level <= maxLevel());
429 return _levelIndexSets[level]->size(codim);
432 int size(
int codim)
const {
433 return _leafIndexSet.size(codim);
436 int size(
int level, GeometryType type)
const {
437 assert(level <= maxLevel());
438 return _levelIndexSets[level]->size(type);
441 int size(GeometryType type)
const {
443 return _leafIndexSet.size(type);
446 const typename Traits::GlobalIdSet& globalIdSet()
const {
450 const typename Traits::LocalIdSet& localIdSet()
const {
454 const typename Traits::LevelIndexSet& levelIndexSet(
int level)
const {
455 if (!_grid.supportLevelIndexSets()) {
456 DUNE_THROW(GridError,
"level index set support not enabled for this grid");
458 assert(level <= maxLevel());
459 assert(_levelIndexSets[level]);
460 return *_levelIndexSets[level];
463 const typename Traits::LeafIndexSet& leafIndexSet()
const {
464 return _leafIndexSet;
474 void globalRefine(
int refCount) {
475 DUNE_THROW(NotImplemented,
"grid modification only allowed on the MultiDomainGrid");
489 bool mark(
int refCount,
const typename Traits::template Codim<0>::Entity& e) {
490 return _grid.mark(refCount,multiDomainEntity(e));
501 int getMark(
const typename Traits::template Codim<0>::Entity& e) {
502 return _grid.getMark(multiDomainEntity(e));
513 DUNE_THROW(NotImplemented,
"grid modification only allowed on the MultiDomainGrid");
524 DUNE_THROW(NotImplemented,
"grid modification only allowed on the MultiDomainGrid");
535 DUNE_THROW(NotImplemented,
"grid modification only allowed on the MultiDomainGrid");
538 int overlapSize(
int level,
int codim)
const {
539 return _grid.overlapSize(level,codim);
542 int overlapSize(
int codim)
const {
543 return _grid.overlapSize(codim);
546 int ghostSize(
int level,
int codim)
const {
547 return _grid.ghostSize(level,codim);
550 int ghostSize(
int codim)
const {
551 return _grid.ghostSize(codim);
554 const typename Traits::Communication& comm()
const {
558 template<
typename DataHandleImp,
typename DataTypeImp>
559 void communicate (CommDataHandleIF<DataHandleImp,DataTypeImp> &data,
560 InterfaceType iftype,
561 CommunicationDirection dir,
564 DataHandleWrapper<CommDataHandleIF<DataHandleImp,DataTypeImp> > datahandle(data,*
this);
565 _grid.hostGrid().levelGridView(level).communicate(datahandle,iftype,dir);
568 template<
typename DataHandleImp,
typename DataTypeImp>
569 void communicate (CommDataHandleIF<DataHandleImp,DataTypeImp> &data,
570 InterfaceType iftype,
571 CommunicationDirection dir)
const
573 DataHandleWrapper<CommDataHandleIF<DataHandleImp,DataTypeImp> > datahandle(data,*
this);
574 _grid.hostGrid().leafGridView().communicate(datahandle,iftype,dir);
577 size_t numBoundarySegments()
const
579 return _grid.numBoundarySegments();
585 const MDGrid& multiDomainGrid()
const {
590 SubDomainIndex domain()
const {
595 if (_grid.supportLevelIndexSets()) {
596 while (_levelIndexSets.size() <=
static_cast<std::size_t
>(maxLevel())) {
597 _levelIndexSets.push_back(std::make_shared<LevelIndexSetImp>(*
this,_grid.levelIndexSet(_levelIndexSets.size())));
602 bool operator==(
const SubDomainGrid& rhs)
const {
603 return (&_grid == &rhs._grid && _subDomain == rhs._subDomain);
611 std::enable_if_t<std::is_same_v<typename MDGrid::Traits::template Codim<EntityType::codimension>::Entity,EntityType>,
int> = 0>
612 typename Traits::template Codim<EntityType::codimension>::Entity subDomainEntity(
const EntityType& mdEntity)
const {
613 return EntityWrapper<EntityType::codimension,dimension,const GridImp>(
this,mdEntity);
619 std::enable_if_t<std::is_same_v<typename MDGrid::Traits::template Codim<EntityType::codimension>::Entity,EntityType>,
int> = 0>
620 static const EntityType&
621 multiDomainEntity(
const EntityType &e) {
627 std::enable_if_t<!std::is_same_v<typename MDGrid::Traits::template Codim<EntityType::codimension>::Entity,EntityType>,
int> = 0>
628 static const typename MDGrid::Traits::template Codim<EntityType::codimension>::Entity &
629 multiDomainEntity(
const EntityType &e) {
630 return e.impl().multiDomainEntity();
633 template<
typename EntityType>
634 static const typename MDGrid::template HostEntity<EntityType>::type& hostEntity(
const EntityType& e) {
635 return e.impl().hostEntity();
638 static const auto& multiDomainIntersection(
const typename Traits::LeafIntersection& is) {
639 return is.impl().multiDomainIntersection();
642 static const auto& multiDomainIntersection(
const typename Traits::LevelIntersection& is) {
643 return is.impl().multiDomainIntersection();
648 typename Traits::LeafIntersectionIterator subDomainIntersectionIterator(
const typename MDGrid::LeafSubDomainInterfaceIterator it)
const {
649 assert(_subDomain == it->subDomain1() || _subDomain == it->subDomain2());
650 if (_subDomain == it->subDomain1())
651 return IntersectionIteratorWrapper<
653 typename GridImp::LeafGridView::IndexSet,
654 typename MDGrid::LeafGridView::IntersectionIterator
656 &this->leafGridView().indexSet(),
657 it->firstMultiDomainIntersectionIterator()
660 return IntersectionIteratorWrapper<
662 typename GridImp::LeafGridView::IndexSet,
663 typename MDGrid::LeafGridView::IntersectionIterator
665 &this->leafGridView().indexSet(),
666 it->secondMultiDomainIntersectionIterator()
670 typename Traits::LevelIntersectionIterator subDomainIntersectionIterator(
const typename MDGrid::LevelSubDomainInterfaceIterator it)
const {
671 assert(_subDomain == it->subDomain1() || _subDomain == it->subDomain2());
672 if (_subDomain == it->subDomain1())
673 return IntersectionIteratorWrapper<
675 typename GridImp::LevelGridView::IndexSet,
676 typename MDGrid::LevelGridView::IntersectionIterator
678 &this->levelGridView(it->firstMultiDomainIntersectionIterator()->inside().level()).indexSet(),
679 it->firstMultiDomainIntersectionIterator()
682 return IntersectionIteratorWrapper<
684 typename GridImp::LevelGridView::IndexSet,
685 typename MDGrid::LevelGridView::IntersectionIterator
687 &this->levelGridView(it->secondMultiDomainIntersectionIterator()->inside().level()).indexSet(),
688 it->secondMultiDomainIntersectionIterator()
692 template<
typename Intersection>
693 IntersectionType intersectionType(
const Intersection& intersection)
const {
694 return intersection.impl().intersectionType();
700 SubDomainIndex _subDomain;
701 GlobalIdSetImp _globalIdSet;
702 LocalIdSetImp _localIdSet;
703 LeafIndexSetImp _leafIndexSet;
704 std::vector<std::shared_ptr<LevelIndexSetImp> > _levelIndexSets;
706 SubDomainGrid(MDGrid& grid, SubDomainIndex subDomain) :
708 _subDomain(subDomain),
709 _globalIdSet(*this,grid.hostGrid().globalIdSet()),
710 _localIdSet(*this,grid.hostGrid().localIdSet()),
711 _leafIndexSet(*this,grid.leafIndexSet())
716 template<
typename EntityType>
717 bool containsMultiDomainEntity(
const EntityType& e)
const {
718 if (_grid.supportLevelIndexSets())
719 return levelIndexSet(e.level()).containsMultiDomainEntity(e);
721 return leafIndexSet().containsMultiDomainEntity(e);
724 template<
typename EntityType>
725 bool containsHostEntity(
const EntityType& e)
const {
726 if (_grid.supportLevelIndexSets())
727 return levelIndexSet(e.level()).containsHostEntity(e);
729 return leafIndexSet().containsHostEntity(e);
732 SubDomainGrid(
const SubDomainGrid& rv);
733 SubDomainGrid& operator=(
const SubDomainGrid& rv);
736 template<
typename Impl>
737 struct DataHandleWrapper
738 :
public Dune::CommDataHandleIF<DataHandleWrapper<Impl>,
739 typename Impl::DataType
743 bool contains(
int dim,
int codim)
const
745 return _impl.contains(dim,codim);
748 bool fixedSize(
int dim,
int codim)
const
754 template<
typename Entity>
755 std::size_t size(
const Entity& e)
const
757 if (_grid.containsHostEntity(e))
758 return _impl.size(_grid.subDomainEntity(_grid._grid.wrapHostEntity(e)));
763 template<
typename MessageBufferImp,
typename Entity>
764 void gather(MessageBufferImp& buf,
const Entity& e)
const
766 if (_grid.containsHostEntity(e))
767 _impl.gather(buf,_grid.subDomainEntity(_grid._grid.wrapHostEntity(e)));
770 template<
typename MessageBufferImp,
typename Entity>
771 void scatter(MessageBufferImp& buf,
const Entity& e, std::size_t n)
773 if (_grid.containsHostEntity(e))
774 _impl.scatter(buf,_grid.subDomainEntity(_grid._grid.wrapHostEntity(e)),n);
777 DataHandleWrapper(Impl& impl,
const SubDomainGrid<MDGrid>& grid)
783 const SubDomainGrid<MDGrid>& _grid;