version 3.11-dev
All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Modules Pages Concepts
facetgridmanager.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-FileCopyrightText: Copyright © DuMux Project contributors, see AUTHORS.md in root folder
5// SPDX-License-Identifier: GPL-3.0-or-later
6//
12#ifndef DUMUX_IO_FACET_GRID_MANAGER_HH
13#define DUMUX_IO_FACET_GRID_MANAGER_HH
14
15#include <limits>
16#include <concepts>
17#include <type_traits>
18#include <vector>
19
20#include <dune/grid/common/mcmgmapper.hh>
21#include <dune/geometry/referenceelements.hh>
22
24#include "gridmanager.hh"
25
26namespace Dumux {
27
28#ifndef DOXYGEN
29namespace Detail::FacetGrid {
30
31static constexpr std::size_t undefinedIndex = std::numeric_limits<std::size_t>::max();
32
33template<typename Grid, typename HostGridView, typename HostGridVertexSet, typename Selector>
34auto fillFactory(Dune::GridFactory<Grid>& factory,
35 const HostGridView& hostGridView,
36 const HostGridVertexSet& hostGridVertexSet,
37 Selector&& selector)
38{
39 static constexpr int domainDim = HostGridView::dimension;
40
41 Dune::MultipleCodimMultipleGeomTypeMapper elementMapper{hostGridView, Dune::mcmgElementLayout()};
42
43 std::vector<unsigned int> localCornerStorage;
44 std::vector<std::size_t> domainToFacetVertex(hostGridVertexSet.size(), undefinedIndex);
45
46 std::size_t vertexCount = 0;
47 for (const auto& element : elements(hostGridView))
48 {
49 const auto& refElement = Dune::referenceElement(element);
50 const auto& elemGeo = element.geometry();
51
52 for (const auto& is : intersections(hostGridView, element))
53 {
54 if (!selector(element, is))
55 continue;
56
57 // visit each facet only once
58 if (!is.boundary())
59 if (elementMapper.index(is.inside()) > elementMapper.index(is.outside()))
60 continue;
61
62 const auto& isGeo = is.geometry();
63 localCornerStorage.clear();
64 localCornerStorage.reserve(isGeo.corners());
65 for (int c = 0; c < isGeo.corners(); ++c)
66 {
67 const auto vIdxLocal = refElement.subEntity(is.indexInInside(), 1, c, domainDim);
68 const auto vIdxGlobal = hostGridVertexSet.index(element.template subEntity<domainDim>(vIdxLocal));
69 if (domainToFacetVertex.at(vIdxGlobal) == undefinedIndex)
70 {
71 factory.insertVertex(elemGeo.global(refElement.position(vIdxLocal, domainDim)));
72 domainToFacetVertex[vIdxGlobal] = vertexCount;
73 vertexCount++;
74 }
75 localCornerStorage.push_back(domainToFacetVertex[vIdxGlobal]);
76 }
77
78 factory.insertElement(isGeo.type(), localCornerStorage);
79 }
80 }
81
82 return domainToFacetVertex;
83}
84
85} // end namespace Detail::FacetGrid
86#endif // DOXYGEN
87
88
89namespace Concept {
90
95template<typename T, typename Element, typename Intersection>
97 = std::invocable<T, const Element&, const Intersection&>
98 and std::convertible_to<bool, std::invoke_result_t<T, const Element&, const Intersection&>>;
99
100} // end namespace Concept
101
108template<typename HG, typename FacetGrid, typename HostGridManager = GridManager<HG>>
110{
111 static constexpr int dim = FacetGrid::dimension;
112 static constexpr int dimWorld = FacetGrid::dimensionworld;
113
114 static_assert(dim == int(HG::dimension) - 1, "Facet grids must have codimension 1 w.r.t host grid");
115 static_assert(dimWorld == int(HG::dimensionworld), "Space dimensions of facet & host grid must match");
116
117 using HostElement = typename HG::template Codim<0>::Entity;
118 using HostIntersection = typename HG::LeafGridView::Intersection;
120
121public:
122 using Grid = FacetGrid;
123 using Vertex = typename Grid::template Codim<dim>::Entity;
124
125 using HostGrid = HG;
126 using HostGridVertex = typename HostGrid::template Codim<dim+1>::Entity;
127
129 template<Concept::FacetSelector<HostElement, HostIntersection> Selector>
130 void init(const HostGrid& hostGrid, const Selector& selector)
131 {
132 hostVertexSet_ = std::make_unique<HostVertexSet>(hostGrid.leafGridView());
133 auto hostToFacetVertexInsertionIndex = Detail::FacetGrid::fillFactory(
135 hostGrid.leafGridView(),
137 selector
138 );
139 facetGrid_ = facetGridFactory_.createGrid();
140 loadBalance();
141
142 facetInsertionToHostVertexIndex_.resize(facetGrid_->leafGridView().size(dim));
143 for (std::size_t hostVertexIndex = 0; hostVertexIndex < hostToFacetVertexInsertionIndex.size(); ++hostVertexIndex)
144 if (hostToFacetVertexInsertionIndex[hostVertexIndex] != Detail::FacetGrid::undefinedIndex)
145 facetInsertionToHostVertexIndex_[hostToFacetVertexInsertionIndex[hostVertexIndex]] = hostVertexIndex;
146 }
147
149 template<Concept::FacetSelector<HostElement, HostIntersection> Selector>
150 void init(const Selector& selector, const std::string& paramGroup = "")
151 {
152 initHostGrid_(paramGroup);
153 init(hostGrid_(), selector);
154 }
155
158 {
159 if (Dune::MPIHelper::getCommunication().size() > 1)
160 this->grid().loadBalance();
161 }
162
165 { return *facetGrid_; }
166
168 const Grid& grid() const
169 { return *facetGrid_; }
170
172 bool hasGridData() const
173 { return false; }
174
177 { return hostVertexSet_->entity(facetInsertionToHostVertexIndex_.at(facetGridFactory_.insertionIndex(v))); }
178
179protected:
180 void initHostGrid_(const std::string& paramGroup)
181 {
182 hostGridManager_ = std::make_unique<HostGridManager>();
183 hostGridManager_->init(paramGroup);
184 }
185
187 { return hostGridManager_->grid(); }
188
189 Dune::GridFactory<Grid> facetGridFactory_;
190 std::unique_ptr<Grid> facetGrid_{nullptr};
191 std::unique_ptr<HostVertexSet> hostVertexSet_{nullptr};
192 std::unique_ptr<HostGridManager> hostGridManager_{nullptr};
193 std::vector<std::size_t> facetInsertionToHostVertexIndex_;
194};
195
196
197} // end namespace Dumux
198
199#endif
Grid manager for grids living on the facets of a host grid.
Definition: facetgridmanager.hh:110
FacetGrid Grid
Definition: facetgridmanager.hh:122
typename HostGrid::template Codim< dim+1 >::Entity HostGridVertex
Definition: facetgridmanager.hh:126
void init(const Selector &selector, const std::string &paramGroup="")
Make the grid and create the host grid internally.
Definition: facetgridmanager.hh:150
HostGridVertex hostGridVertex(const Vertex &v) const
Return the host grid vertex that overlaps with the given facet grid vertex.
Definition: facetgridmanager.hh:176
void loadBalance()
Call loadBalance() function of the grid.
Definition: facetgridmanager.hh:157
std::unique_ptr< HostGridManager > hostGridManager_
Definition: facetgridmanager.hh:192
std::unique_ptr< HostVertexSet > hostVertexSet_
Definition: facetgridmanager.hh:191
Dune::GridFactory< Grid > facetGridFactory_
Definition: facetgridmanager.hh:189
HostGrid & hostGrid_()
Definition: facetgridmanager.hh:186
const Grid & grid() const
Returns a const reference to the grid.
Definition: facetgridmanager.hh:168
void init(const HostGrid &hostGrid, const Selector &selector)
Make the grid using an externally created host grid.
Definition: facetgridmanager.hh:130
void initHostGrid_(const std::string &paramGroup)
Definition: facetgridmanager.hh:180
std::vector< std::size_t > facetInsertionToHostVertexIndex_
Definition: facetgridmanager.hh:193
std::unique_ptr< Grid > facetGrid_
Definition: facetgridmanager.hh:190
Grid & grid()
Returns a reference to the grid.
Definition: facetgridmanager.hh:164
typename Grid::template Codim< dim >::Entity Vertex
Definition: facetgridmanager.hh:123
bool hasGridData() const
Return true if grid data is available.
Definition: facetgridmanager.hh:172
HG HostGrid
Definition: facetgridmanager.hh:125
An interface for a set of geometric entities based on a GridView.
Definition: geometricentityset.hh:37
Concept for selecting grid intersections to be included in a facet grid.
Definition: facetgridmanager.hh:97
An interface for a set of geometric entities.
Contains the grid manager class that creates the grids in the context of hybrid-dimensional coupled m...
Definition: adapt.hh:17