version 3.8
vertexmapper.hh
Go to the documentation of this file.
1// -*- mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
2// vi: set et ts=4 sw=4 sts=4:
3//
4// SPDX-FileCopyrightInfo: Copyright © DuMux Project contributors, see AUTHORS.md in root folder
5// SPDX-License-Identifier: GPL-3.0-or-later
6//
7
13#ifndef DUMUX_ENRICHED_VERTEX_DOF_MAPPER_HH
14#define DUMUX_ENRICHED_VERTEX_DOF_MAPPER_HH
15
16#include <vector>
17
18#include <dune/common/exceptions.hh>
19#include <dune/common/timer.hh>
20#include <dune/grid/common/mcmgmapper.hh>
21
22#include "enrichmenthelper.hh"
23
24namespace Dumux {
25
34{
35
36public:
51 template< class GridView,
52 class VertexMapper,
53 class CodimOneGridView,
55 static void markVerticesForEnrichment(std::vector<bool>& vertexMarkers,
56 const GridView& gridView,
57 const VertexMapper& vertexMapper,
58 const CodimOneGridView& codimOneGridView,
59 const CodimOneGridAdapter& codimOneGridAdapter)
60 {
61 static constexpr int dim = GridView::dimension;
62 static_assert(CodimOneGridView::dimension == dim-1, "Grid dimension mismatch");
63
64 // reset the markers
65 vertexMarkers.assign(gridView.size(dim), false);
66
67 // first find all bulk grid vertices on the boundary
68 std::vector<bool> isOnBoundary(gridView.size(dim), false);
69 for (const auto& e : elements(gridView))
70 {
71 const auto refElem = referenceElement(e);
72 for (const auto& is : intersections(gridView, e))
73 if (is.boundary())
74 for (int i = 0; i < is.geometry().corners(); ++i)
75 isOnBoundary[ vertexMapper.subIndex( e,
76 refElem.subEntity(is.indexInInside(), 1, i, dim),
77 dim ) ] = true;
78 }
79
80 // for now, set all markers to true for vertices on codim one grid
81 for (const auto& vertex : vertices(codimOneGridView))
82 vertexMarkers[codimOneGridAdapter.bulkGridVertexIndex(vertex)] = true;
83
84 // unmark where necessary
85 for (const auto& codimOneElement : elements(codimOneGridView))
86 {
87 // if a codimension one element has less than two embedments we do not need to enrich
88 if (codimOneGridAdapter.numEmbedments(codimOneElement) < 2)
89 for (int i = 0; i < codimOneElement.subEntities(dim-1); ++i)
90 vertexMarkers[ codimOneGridAdapter.bulkGridVertexIndex(codimOneElement.template subEntity<dim-1>(i)) ] = false;
91
92 // otherwise, we check for immersed boundaries where we also must not enrich
93 else
94 {
95 const auto refElem = referenceElement(codimOneElement);
96 for (const auto& intersection : intersections(codimOneGridView, codimOneElement))
97 {
98 // skip if intersection is not on boundary
99 if (!intersection.boundary())
100 continue;
101
102 // obtain all grid indices of the intersection corners
103 const auto numCorners = intersection.geometry().corners();
104 std::vector<typename GridView::IndexSet::IndexType> vertexIndices(numCorners);
105 for (int i = 0; i < numCorners; ++i)
106 {
107 const auto vIdxLocal = refElem.subEntity(intersection.indexInInside(), 1, i, dim-1);
108 vertexIndices[i] = codimOneGridAdapter.bulkGridVertexIndex( codimOneElement.template subEntity<dim-1>(vIdxLocal) );
109 }
110
111 // if any of the vertices is on an immersed boundary, we must not enrich any of them
112 if (std::any_of(vertexIndices.begin(), vertexIndices.end(), [&isOnBoundary] (auto idx) { return !isOnBoundary[idx]; }))
113 std::for_each(vertexIndices.begin(), vertexIndices.end(), [&vertexMarkers] (auto idx) { vertexMarkers[idx] = false; });
114 }
115 }
116 }
117 }
118};
119
128template<class GV>
130{
131 static constexpr int dim = GV::dimension;
132 static_assert(dim > 1, "Vertex dof enrichment mapper currently only works for dim > 1!");
133
134 using GIType = typename GV::IndexSet::IndexType;
135 using Vertex = typename GV::template Codim<dim>::Entity;
136 using Element = typename GV::template Codim<0>::Entity;
137 using MCMGMapper = Dune::MultipleCodimMultipleGeomTypeMapper<GV>;
138
139public:
141 using GridView = GV;
143 using GridIndexType = GIType;
144
146 EnrichedVertexDofMapper(const GV& gridView)
147 : gridView_(gridView)
148 , elementMapper_(gridView, Dune::mcmgElementLayout())
149 , vertexMapper_(gridView, Dune::mcmgVertexLayout())
150 {
151 initialize_();
152 }
153
155 EnrichedVertexDofMapper(const GV& gridView, Dune::MCMGLayout layout)
156 : EnrichedVertexDofMapper(gridView)
157 {
158 if ( !( static_cast<bool>(layout(Dune::GeometryTypes::vertex, dim)) ) )
159 DUNE_THROW(Dune::InvalidStateException, "Vertex mapper only makes sense for vertex layout!");
160 }
161
163 GridIndexType subIndex(const Element& e, unsigned int i, unsigned int codim) const
164 {
165 assert(codim == dim && "Only element corners can be mapped by this mapper");
166 return indexMap_[elementMapper_.index(e)][i];
167 }
168
170 GridIndexType vertexIndex(const Element& e, unsigned int i, unsigned int codim) const
171 {
172 assert(codim == dim && "Only element corners can be mapped by this mapper");
173 return vertexMapper_.subIndex(e, i, codim);
174 }
175
177 GridIndexType vertexIndex(const Vertex& v) const
178 {
179 assert(Vertex::Geometry::mydimension == 0 && "Only vertices can be mapped by this mapper");
180 return vertexMapper_.index(v);
181 }
182
187 template< class EntityType >
188 GridIndexType index(const EntityType& e) const
189 {
190 if (hasEnrichedVertices_)
191 DUNE_THROW(Dune::InvalidStateException, "Index map contains enriched vertex dofs. Direct mapping from vertex to index not possible.");
192
193 assert(EntityType::Geometry::mydimension == 0 && "Only vertices can be mapped by this mapper");
194 return vertexMapper_.index(e);
195 }
196
198 std::size_t size() const
199 { return size_; }
200
202 bool isEnriched(const Vertex& v)
203 { return isEnriched_[ vertexMapper_.index(v) ]; }
204
207 void update(const GV& gridView)
208 {
209 gridView_ = gridView;
210 initialize_();
211 }
212
213 void update(GV&& gridView)
214 {
215 gridView_ = std::move(gridView);
216 initialize_();
217 }
218
230 template<class CodimOneGridView, class CodimOneGridAdapter>
231 void enrich(const CodimOneGridView& codimOneGridView,
232 const CodimOneGridAdapter& codimOneGridAdapter,
233 bool verbose = false)
234 {
235 static const int codimOneDim = CodimOneGridView::dimension;
236 static_assert(codimOneDim == dim-1, "Grid dimension mismatch!");
237 static_assert(codimOneDim == 2 || codimOneDim == 1, "Inadmissible codimension one grid dimension");
238 static_assert(int(CodimOneGridView::dimensionworld) == int(GV::dimensionworld), "Grid world dimension mismatch");
239
240 // keep track of time
241 Dune::Timer watch;
242
243 // mark vertices for enrichment using the indicator
244 EnrichmentIndicator::markVerticesForEnrichment(isEnriched_, gridView_, vertexMapper_, codimOneGridView, codimOneGridAdapter);
245
246 // let the helper class do the enrichment of the index map
248 isEnriched_,
249 gridView_,
250 vertexMapper_,
251 elementMapper_,
252 codimOneGridView,
253 codimOneGridAdapter);
254
255 // check if new index map contains enriched dofs
256 hasEnrichedVertices_ = std::any_of(isEnriched_.begin(), isEnriched_.end(), [] (bool isEnriched) { return isEnriched; });
257
258 if (verbose)
259 std::cout << "Vertex dof enrichment took " << watch.elapsed() << " seconds." << std::endl;
260 }
261
262private:
263
265 void initialize_()
266 {
267 size_ = gridView_.size(dim);
268 hasEnrichedVertices_ = false;
269 indexMap_.resize(gridView_.size(0));
270 isEnriched_.resize(gridView_.size(dim), false);
271 for (const auto& e : elements(gridView_))
272 {
273 const auto numCorners = e.geometry().corners();
274 const auto eIdxGlobal = elementMapper_.index(e);
275 indexMap_[eIdxGlobal].resize(numCorners);
276 for (unsigned int i = 0; i < numCorners; ++i)
277 indexMap_[eIdxGlobal][i] = vertexMapper_.subIndex(e, i, dim);
278 }
279 }
280
281 // data members
282 std::size_t size_;
283 GV gridView_;
284 MCMGMapper elementMapper_;
285 MCMGMapper vertexMapper_;
286 bool hasEnrichedVertices_;
287 std::vector<bool> isEnriched_;
288 std::vector< std::vector<GIType> > indexMap_;
289};
290
291} // end namespace Dumux
292
293#endif
Adapter that allows retrieving information on a d-dimensional grid for entities of a (d-1)-dimensiona...
Definition: codimonegridadapter.hh:40
std::size_t numEmbedments(const FacetGridElement &e) const
Returns the number of d-dimensional elements in which the given (d-1)-dimensional element is embedded...
Definition: codimonegridadapter.hh:226
BulkIndexType bulkGridVertexIndex(const FacetGridVertex &v) const
Returns the index within the d-dimensional grid of a vertex of the (d-1)-dimensional grid.
Definition: codimonegridadapter.hh:133
A vertex mapper that allows for enrichment of nodes. Indication on where to enrich the nodes is done ...
Definition: vertexmapper.hh:130
void enrich(const CodimOneGridView &codimOneGridView, const CodimOneGridAdapter &codimOneGridAdapter, bool verbose=false)
Enriches the dof map subject to a (dim-1)-dimensional grid.
Definition: vertexmapper.hh:231
std::size_t size() const
returns the number of dofs managed by this mapper
Definition: vertexmapper.hh:198
GridIndexType vertexIndex(const Element &e, unsigned int i, unsigned int codim) const
map nodal subentity of codim 0 entity to the grid vertex index
Definition: vertexmapper.hh:170
GridIndexType index(const EntityType &e) const
Definition: vertexmapper.hh:188
void update(const GV &gridView)
Definition: vertexmapper.hh:207
EnrichedVertexDofMapper(const GV &gridView)
the constructor
Definition: vertexmapper.hh:146
GridIndexType vertexIndex(const Vertex &v) const
map nodal entity to the grid vertex index
Definition: vertexmapper.hh:177
GIType GridIndexType
export the grid index type
Definition: vertexmapper.hh:143
GridIndexType subIndex(const Element &e, unsigned int i, unsigned int codim) const
map nodal subentity of codim 0 entity to the grid dof
Definition: vertexmapper.hh:163
GV GridView
export the underlying grid view type
Definition: vertexmapper.hh:141
EnrichedVertexDofMapper(const GV &gridView, Dune::MCMGLayout layout)
constructor taking a layout as additional argument (for compatibility)
Definition: vertexmapper.hh:155
bool isEnriched(const Vertex &v)
returns true if a vertex dof had been enriched
Definition: vertexmapper.hh:202
void update(GV &&gridView)
Definition: vertexmapper.hh:213
An indicator class used to mark vertices for enrichment. This implementation marks all vertices of a ...
Definition: vertexmapper.hh:34
static void markVerticesForEnrichment(std::vector< bool > &vertexMarkers, const GridView &gridView, const VertexMapper &vertexMapper, const CodimOneGridView &codimOneGridView, const CodimOneGridAdapter &codimOneGridAdapter)
Function that marks vertices for enrichment. This implementation works on the basis of a facet-confor...
Definition: vertexmapper.hh:55
static std::size_t enrich(IndexMap &indexMap, const std::vector< bool > &vertexMarkers, const GridView &gridView, const MCMGMapper &vertexMapper, const MCMGMapper &elementMapper, const CodimOneGridView &codimOneGridView, const CodimOneGridAdapter &codimOneGridAdapter)
Enriches the dof map subject to a (dim-1)-dimensional grid.
Definition: enrichmenthelper.hh:77
std::size_t numCorners(Shape shape)
Returns the number of corners of a given geometry.
Definition: throatproperties.hh:220
Definition: adapt.hh:17
Definition: common/pdesolver.hh:24