1#ifndef DUNE_PDELAB_COMMON_PARTITIONVIEWENTITYSET_HH
2#define DUNE_PDELAB_COMMON_PARTITIONVIEWENTITYSET_HH
13#include <dune/common/iteratorrange.hh>
14#include <dune/geometry/referenceelements.hh>
17#include <dune/grid/common/partitionset.hh>
18#include <dune/grid/common/rangegenerators.hh>
30 using Dune::descendantElements;
31 using Dune::intersections;
33 template<
typename GV,
typename P>
34 class PartitionViewEntitySet;
36 template<
typename GV,
typename P>
37 class PartitionViewEntitySetIndexSet;
39 template<
typename GV,
typename P>
40 struct PartitionViewEntitySetTraits
43 using Partitions =
typename std::decay<P>::type;
45 using Grid =
typename GV::Traits::Grid;
47 using EntitySet = Dune::PDELab::PartitionViewEntitySet<GV,P>;
48 using IndexSet = PartitionViewEntitySetIndexSet<GV,Partitions>;
49 using BaseIndexSet =
typename GV::Traits::IndexSet;
51 using Element =
typename GV::template Codim<0>::Entity;
53 using Intersection =
typename GV::Traits::Intersection;
55 using IntersectionIterator =
typename GV::Traits::IntersectionIterator;
57 using CollectiveCommunication =
typename GV::Traits::CollectiveCommunication;
59 using size_type = std::size_t;
62 using Index =
typename BaseIndexSet::IndexType;
66 using CodimMask = std::bitset<GV::dimension + 1>;
70 constexpr static Index invalidIndex()
72 return ~static_cast<Index>(0ull);
75 static const bool conforming = GV::Traits::conforming;
77 static const dim_type dimension = GV::dimension;
79 static const dim_type dimensionworld = GV::dimensionworld;
81 template<dim_type codim>
85 using Iterator =
typename GV::template Codim<codim>::template Partition<Partitions::partitionIterator()>::Iterator;
87 using Entity =
typename GV::template Codim<codim>::Entity;
89 using Geometry =
typename GV::template Codim<codim>::Geometry;
91 using LocalGeometry =
typename GV::template Codim<codim>::LocalGeometry;
93 template<PartitionIteratorType pitype>
97 using Iterator =
typename GV::template Codim<codim>::template Partition<pitype>::Iterator;
106 template<
typename GV,
typename P>
107 class PartitionViewEntitySet
112 using Traits = PartitionViewEntitySetTraits<GV,P>;
114 using Partitions =
typename Traits::Partitions;
115 using Grid =
typename Traits::Grid;
116 using GridView =
typename Traits::GridView;
117 using IndexSet =
typename Traits::IndexSet;
118 using BaseIndexSet =
typename Traits::BaseIndexSet;
119 using Element =
typename Traits::Element;
120 using Intersection =
typename Traits::Intersection;
121 using IntersectionIterator =
typename Traits::IntersectionIterator;
122 using CollectiveCommunication =
typename Traits::CollectiveCommunication;
123 using CodimMask =
typename Traits::CodimMask;
124 using CoordinateField =
typename Traits::CoordinateField;
125 using size_type =
typename Traits::size_type;
126 using dim_type =
typename Traits::dim_type;
128 using ctype = CoordinateField;
130 static const bool conforming = Traits::conforming;
131 static const dim_type dimension = Traits::dimension;
132 static const dim_type dimensionworld = Traits::dimensionworld;
134 template<dim_type codim>
135 using Codim =
typename Traits::template Codim<codim>;
137 constexpr static Partitions partitions()
142 constexpr static CodimMask allCodims()
147 const Grid& grid()
const
149 return gridView().grid();
153 const IndexSet& indexSet()
const
159 const BaseIndexSet& baseIndexSet()
const
161 return indexSet().baseIndexSet();
164 template<dim_type codim>
165 typename Codim<codim>::Iterator
168 return gridView().template begin<codim,Partitions::partitionIterator()>();
171 template<dim_type codim>
172 typename Codim<codim>::Iterator
175 return gridView().template end<codim,Partitions::partitionIterator()>();
178 template<dim_type codim, PartitionIteratorType pitype>
179 typename GV::template Codim<codim>::template Partition<pitype>::Iterator
182 return gridView().template begin<codim,pitype>();
185 template<dim_type codim, PartitionIteratorType pitype>
186 typename GV::template Codim<codim>::template Partition<pitype>::Iterator
189 return gridView().template end<codim,pitype>();
192 size_type size(dim_type codim)
const
194 return indexSet().size(codim);
197 size_type size(
const GeometryType&
gt)
const
199 return indexSet().size(
gt);
202 template<
typename Entity>
203 bool contains(
const Entity& e)
const
205 return indexSet().contains(e);
208 bool contains(dim_type codim)
const
210 return indexSet().contains(codim);
213 bool contains(
const GeometryType&
gt)
const
215 return indexSet().contains(
gt);
218 IntersectionIterator ibegin(
const typename Codim<0>::Entity& entity)
const
220 return gridView().ibegin(entity);
223 IntersectionIterator iend(
const typename Codim<0>::Entity& entity)
const
225 return gridView().iend(entity);
228 const CollectiveCommunication& comm()
const
230 return gridView().comm();
234 size_type overlapSize(dim_type codim)
const
240 size_type ghostSize(dim_type codim)
const
245 template<
typename DataHandle>
248 gridView().communicate(data,iftype,dir);
252 const GridView& gridView()
const
254 return indexSet().gridView();
257 PartitionViewEntitySet(
const GridView& gv, CodimMask supported_codims)
258 : _index_set(
std::make_shared<IndexSet>(gv,supported_codims,true))
261 explicit PartitionViewEntitySet(
const GridView& gv,
bool initialize =
true)
262 : _index_set(
std::make_shared<IndexSet>(gv,CodimMask(initialize ? ~0ull : 0ull),initialize))
272 void addCodim(dim_type codim)
274 _index_set->addCodim(codim);
278 void removeCodim(dim_type codim)
280 _index_set->removeCodim(codim);
284 bool needsUpdate()
const
286 return _index_set->needsUpdate();
298 bool update(
bool force =
false)
300 return _index_set->update(force);
305 std::shared_ptr<IndexSet> _index_set;
309 template<
typename GV,
typename P>
310 class PartitionViewEntitySetIndexSetBase
313 template<
typename,
typename>
314 friend class PartitionViewEntitySet;
318 using Traits = PartitionViewEntitySetTraits<GV,P>;
320 using Partitions =
typename Traits::Partitions;
321 using Grid =
typename Traits::Grid;
322 using GridView =
typename Traits::GridView;
323 using BaseIndexSet =
typename Traits::BaseIndexSet;
324 using size_type =
typename Traits::size_type;
325 using dim_type =
typename Traits::dim_type;
326 using Index =
typename Traits::Index;
327 using Types =
typename Traits::Types;
328 using CodimMask =
typename Traits::CodimMask;
330 using IndexType = Index;
332 constexpr static Index invalidIndex()
334 return Traits::invalidIndex();
337 template<dim_type codim>
338 using Codim =
typename Traits::template Codim<codim>;
340 PartitionViewEntitySetIndexSetBase(
const PartitionViewEntitySetIndexSetBase&) =
delete;
341 PartitionViewEntitySetIndexSetBase& operator=(
const PartitionViewEntitySetIndexSetBase&) =
delete;
346 bool update(
bool force)
348 if (!(_needs_update || force))
350 std::fill(_gt_offsets.begin(),_gt_offsets.end(),0);
351 std::fill(_mapped_gt_offsets.begin(),_mapped_gt_offsets.end(),0);
352 _active_geometry_types.reset();
353 _geometry_types.resize(0);
354 for (dim_type codim = 0; codim <= GV::dimension; ++codim)
356 if (!_wanted_codims.test(codim))
358 for (
const auto&
gt : baseIndexSet().types(codim))
361 _gt_offsets[gt_index + 1] = baseIndexSet().size(
gt);
362 _geometry_types.push_back(
gt);
363 _active_geometry_types.set(gt_index);
366 for (dim_type codim = 0; codim <= GV::dimension; ++codim)
368 auto range = std::equal_range(
369 _geometry_types.begin(),
370 _geometry_types.end(),
372 [](
const GeometryType& x,
const GeometryType& y)
375 return y.dim() < x.dim();
377 _per_codim_geometry_types[codim] = {range.first,range.second};
380 std::partial_sum(_gt_offsets.begin(),_gt_offsets.end(),_gt_offsets.begin());
381 _active_codims = _wanted_codims;
382 _needs_update =
false;
388 size_type size(GeometryType
gt)
const
390 assert(!needsUpdate());
392 return _mapped_gt_offsets[gt_index + 1] - _mapped_gt_offsets[gt_index];
395 size_type size(dim_type codim)
const
397 assert(!needsUpdate());
398 auto dim = GV::dimension;
403 template<
typename Entity>
404 bool contains(
const Entity& e)
const
406 return Partitions::contains(e.partitionType()) ? baseIndexSet().contains(e) :
false;
409 bool contains(dim_type codim)
const
411 return _active_codims.test(codim);
414 bool contains(
const GeometryType&
gt)
const
419 const BaseIndexSet& baseIndexSet()
const
421 return _gv.indexSet();
424 Types types(dim_type codim)
const
426 assert(!needsUpdate());
427 return _per_codim_geometry_types[codim];
432 assert(!needsUpdate());
433 return {_geometry_types.begin(),_geometry_types.end()};
436 PartitionViewEntitySetIndexSetBase(
const GV& gv, CodimMask wanted_codims)
438 , _needs_update(true)
439 , _wanted_codims(wanted_codims)
442 const GridView& gridView()
const
447 bool needsUpdate()
const
449 return _needs_update;
456 _needs_update =
true;
457 _wanted_codims.reset();
460 void addCodim(dim_type codim)
462 _wanted_codims.set(codim);
463 _needs_update = _wanted_codims != _active_codims || _wanted_codims.none();
466 void removeCodim(dim_type codim)
468 _wanted_codims.reset(codim);
469 _needs_update = _wanted_codims != _active_codims || _wanted_codims.none();
474 CodimMask _wanted_codims;
476 CodimMask _active_codims;
482 std::vector<GeometryType> _geometry_types;
483 std::array<Types,GV::dimension + 1> _per_codim_geometry_types;
487 template<
typename GV,
typename P>
488 class PartitionViewEntitySetIndexSet
489 :
public PartitionViewEntitySetIndexSetBase<GV,P>
492 using Base = PartitionViewEntitySetIndexSetBase<GV,P>;
494 template<
typename,
typename>
495 friend class PartitionViewEntitySet;
499 using typename Base::Index;
500 using typename Base::Partitions;
501 using typename Base::size_type;
502 using typename Base::dim_type;
504 using typename Base::Grid;
506 using Base::gridView;
507 using Base::baseIndexSet;
508 using Base::invalidIndex;
509 using Base::contains;
510 using typename Base::CodimMask;
511 using Base::needsUpdate;
520 template<dim_type dim = 0>
523 return Capabilities::hasEntityIterator<Grid,dim>::v && hasAllEntityIterators(
Dune::Dim<dim+1>{});
526 bool update(
bool force)
528 if (!Base::update(force))
530 _indices.assign(_gt_offsets.back(),invalidIndex());
531 _mapped_gt_offsets[0] = 0;
532 update_codims(std::integral_constant<
bool,hasAllEntityIterators()>{});
533 std::partial_sum(_mapped_gt_offsets.begin(),_mapped_gt_offsets.end(),_mapped_gt_offsets.begin());
537 void update_codims(std::true_type)
545 template<dim_type cd>
548 if (_active_codims.test(codim))
553 if (Partitions::contains(e.partitionType()))
554 _indices[_gt_offsets[gt_index] + baseIndexSet().index(e)] = _mapped_gt_offsets[gt_index + 1]++;
560 void update_codims(std::false_type)
562 std::fill(_indices.begin(),_indices.end(),invalidIndex());
564 auto& index_set = baseIndexSet();
568 if (!Partitions::contains(e.partitionType()))
574 if (!_active_codims.test(codim))
577 size_type sub_entity_count = ref_el.size(codim);
579 for(size_type i = 0; i < sub_entity_count; ++i)
581 auto gt = ref_el.type(i,codim);
583 auto index = index_set.subIndex(e,i,codim);
584 if (_indices[_gt_offsets[gt_index] + index] == invalidIndex())
585 _indices[_gt_offsets[gt_index] + index] = _mapped_gt_offsets[gt_index + 1]++;
595 Index index(
const E& e)
const
597 assert(!needsUpdate());
598 assert(Partitions::contains(e.partitionType()));
599 assert(contains(e.type()));
601 return _indices[_gt_offsets[gt_index] + baseIndexSet().index(e)];
605 Index subIndex(
const E& e, size_type i, dim_type codim)
const
607 assert(!needsUpdate());
608 assert(Partitions::contains(e.partitionType()));
610 assert(contains(
gt));
612 return _indices[_gt_offsets[gt_index] + baseIndexSet().subIndex(e,i,codim)];
617 Index uniqueIndex(
const E& e)
const
619 assert(!needsUpdate());
620 assert(Partitions::contains(e.partitionType()));
621 assert(contains(e.type()));
623 return _indices[_gt_offsets[gt_index] + baseIndexSet().index(e)] + _mapped_gt_offsets[gt_index];
627 Index uniqueSubIndex(
const E& e, size_type i, dim_type codim)
const
629 assert(!needsUpdate());
630 assert(Partitions::contains(e.partitionType()));
632 assert(contains(
gt));
634 return _indices[_gt_offsets[gt_index] + baseIndexSet().subIndex(e,i,codim)] + _mapped_gt_offsets[gt_index];
638 PartitionViewEntitySetIndexSet(
const GV& gv, CodimMask wanted_codims,
bool initialize)
639 : Base(gv,wanted_codims)
647 using Base::_active_codims;
648 using Base::_gt_offsets;
649 using Base::_mapped_gt_offsets;
651 std::vector<Index> _indices;
655 template<
typename GV>
656 class PartitionViewEntitySetIndexSet<GV,Partitions::
All>
657 :
public PartitionViewEntitySetIndexSetBase<GV,Partitions::All>
660 using Base = PartitionViewEntitySetIndexSetBase<GV,Dune::Partitions::All>;
662 template<
typename,
typename>
663 friend class Dune::PDELab::PartitionViewEntitySet;
667 using typename Base::Index;
668 using typename Base::Partitions;
669 using typename Base::size_type;
670 using typename Base::dim_type;
671 using typename Base::CodimMask;
673 using Base::baseIndexSet;
674 using Base::contains;
678 bool update(
bool force)
680 if (!Base::update(force))
682 _mapped_gt_offsets[0] = 0;
683 for (
const auto&
gt : Base::types())
685 std::partial_sum(_mapped_gt_offsets.begin(),_mapped_gt_offsets.end(),_mapped_gt_offsets.begin());
692 Index index(
const E& e)
const
694 assert(contains(e.type()));
695 return baseIndexSet().index(e);
699 Index uniqueIndex(
const E& e)
const
701 assert(contains(e.type()));
706 Index subIndex(
const E& e, size_type i, dim_type codim)
const
710 assert(contains(
gt));
712 return baseIndexSet().subIndex(e,i,codim);
716 Index uniqueSubIndex(
const E& e, size_type i, dim_type codim)
const
719 assert(contains(
gt));
723 PartitionViewEntitySetIndexSet(
const GV& gv, CodimMask wanted_codims,
bool initialize =
true)
724 : Base(gv,wanted_codims)
732 using Base::_mapped_gt_offsets;
736 template<
typename GV>
737 using AllEntitySet = PartitionViewEntitySet<GV,Partitions::All>;
739 template<
typename GV>
740 using OverlappingEntitySet = PartitionViewEntitySet<GV,Partitions::InteriorBorderOverlapFront>;
742 template<
typename GV>
743 using NonOverlappingEntitySet = PartitionViewEntitySet<GV,Partitions::InteriorBorder>;
752 using type = std::false_type;
755 template<
typename GV,
typename P>
756 struct _isEntitySet<PartitionViewEntitySet<GV,P>>
758 using type = std::true_type;
767 using isEntitySet =
typename impl::_isEntitySet<T>::type;
static constexpr std::size_t index(const GeometryType >)
Compute the index for the given geometry type over all dimensions.
Definition: typeindex.hh:133
static constexpr std::size_t offset(std::size_t dim)
Compute the starting index for a given dimension including irregular geometry types.
Definition: typeindex.hh:108
static constexpr std::size_t size(std::size_t maxdim)
Compute total number of geometry types up to and including the given dimension.
Definition: typeindex.hh:120
@ dimension
The dimension of the grid.
Definition: grid.hh:387
ct ctype
Define type used for coordinates in grid module.
Definition: grid.hh:522
Iterator const_iterator
The iterator belonging to this range.
Definition: iteratorrange.hh:31
A set of traits classes to store static information about grid implementation.
@ conforming
Output conforming data.
Definition: common.hh:72
bool gt(const T &first, const T &second, typename EpsilonType< T >::Type epsilon)
test if first greater than second
Definition: float_cmp.cc:156
static constexpr bool isEntitySet()
Check if F models the GridFunction concept with given signature and entity set.
Definition: functionconcepts.hh:230
constexpr GeometryType none(unsigned int dim)
Returns a GeometryType representing a singular of dimension dim.
Definition: type.hh:785
constexpr Overlap overlap
PartitionSet for the overlap partition.
Definition: partitionset.hh:276
PartitionSet<... > All
Type of PartitionSet for all partitions.
Definition: partitionset.hh:266
constexpr All all
PartitionSet for all partitions.
Definition: partitionset.hh:294
constexpr Ghost ghost
PartitionSet for the ghost partition.
Definition: partitionset.hh:282
Dune namespace.
Definition: alignedallocator.hh:14
Static tag representing a dimension.
Definition: dimension.hh:14
static const ReferenceElement & general(const GeometryType &type)
get general reference elements
Definition: referenceelements.hh:196
Helper classes to provide indices for geometrytypes for use in a vector.
Various macros to work with Dune module version numbers.