version 3.9-dev
staggered/freeflow/gridvolumevariables.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//
12#ifndef DUMUX_DISCRETIZATION_STAGGERED_GRID_VOLUMEVARIABLES_HH
13#define DUMUX_DISCRETIZATION_STAGGERED_GRID_VOLUMEVARIABLES_HH
14
15#include <dune/common/exceptions.hh>
16#include <dune/common/rangeutilities.hh>
17
18// make the local view function available whenever we use this class
22
23namespace Dumux {
24
25template<class P, class VV>
27{
28 using Problem = P;
29 using VolumeVariables = VV;
30 using PrimaryVariables = typename VV::PrimaryVariables;
31
32 template<class GridVolumeVariables, bool cachingEnabled>
34
37 template<class Problem, class SolutionVector, class Element, class SubControlVolumeFace>
39 const SolutionVector& sol,
40 const Element& element,
41 const SubControlVolumeFace& scvf)
42 {
43 using CellCenterPrimaryVariables = typename SolutionVector::value_type;
44 using Indices = typename VolumeVariables::Indices;
45 static constexpr auto dim = PrimaryVariables::dimension - CellCenterPrimaryVariables::dimension;
46 static constexpr auto offset = dim;
47
48 const auto bcTypes = problem.boundaryTypes(element, scvf);
49 PrimaryVariables boundaryPriVars(0.0);
50
51 // make sure to not use outflow BC for momentum balance
52 for(int i = 0; i < dim; ++i)
53 {
54 if(bcTypes.isOutflow(Indices::velocity(i)))
55 DUNE_THROW(Dune::InvalidStateException, "Outflow condition cannot be used for velocity. Set only a Dirichlet value for pressure instead.");
56 }
57
58 if(bcTypes.isOutflow(Indices::pressureIdx))
59 DUNE_THROW(Dune::InvalidStateException, "Outflow condition cannot be used for pressure. Set only a Dirichlet value for velocity instead.");
60
61 // Determine the pressure value at a boundary with a Dirichlet condition for velocity.
62 // This just takes the value of the adjacent inner cell.
63 if(bcTypes.isDirichlet(Indices::velocity(scvf.directionIndex())))
64 {
65 if(bcTypes.isDirichlet(Indices::pressureIdx))
66 DUNE_THROW(Dune::InvalidStateException, "A Dirichlet condition for velocity must not be combined with a Dirichlet condition for pressure");
67 else
68 boundaryPriVars[Indices::pressureIdx] = sol[scvf.insideScvIdx()][Indices::pressureIdx - offset];
69 // TODO: pressure could be extrapolated to the boundary
70 }
71
72 // Determine the pressure value for a boundary with a Dirichlet condition for pressure.
73 // Takes a value specified in the problem.
74 if(bcTypes.isDirichlet(Indices::pressureIdx))
75 {
76 if(bcTypes.isDirichlet(Indices::velocity(scvf.directionIndex())))
77 DUNE_THROW(Dune::InvalidStateException, "A Dirichlet condition for velocity must not be combined with a Dirichlet condition for pressure");
78 else
79 boundaryPriVars[Indices::pressureIdx] = problem.dirichlet(element, scvf)[Indices::pressureIdx];
80 }
81
82 // Return for isothermal single-phase systems ...
83 if(CellCenterPrimaryVariables::dimension == 1)
84 return boundaryPriVars;
85
86 // ... or handle values for components, temperature, etc.
87 for(int eqIdx = offset; eqIdx < PrimaryVariables::dimension; ++eqIdx)
88 {
89 if(eqIdx == Indices::pressureIdx)
90 continue;
91
92 if(bcTypes.isDirichlet(eqIdx))
93 boundaryPriVars[eqIdx] = problem.dirichlet(element, scvf)[eqIdx];
94 else if(bcTypes.isOutflow(eqIdx) || bcTypes.isSymmetry() || bcTypes.isNeumann(eqIdx))
95 boundaryPriVars[eqIdx] = sol[scvf.insideScvIdx()][eqIdx - offset];
96 }
97
98 // make sure that a potential outflow condition is set for all components
99 std::array<bool, VolumeVariables::numFluidComponents() - 1> isComponentOutflow;
100 for(int compIdx = 1; compIdx < VolumeVariables::numFluidComponents(); ++compIdx)
101 {
102 const auto eqIdx = VolumeVariables::Indices::conti0EqIdx + compIdx;
103 isComponentOutflow[compIdx -1] = bcTypes.isOutflow(eqIdx);
104 }
105
106 if(Dune::any_true(isComponentOutflow) && !Dune::all_true(isComponentOutflow))
107 DUNE_THROW(Dune::InvalidStateException, "Outflow condition must be set for all components!");
108
109 return boundaryPriVars;
110 }
111};
112
117template<class Traits, bool cachingEnabled>
119
125template<class Traits>
126class StaggeredGridVolumeVariables<Traits, /*cachingEnabled*/true>
127{
129 using PrimaryVariables = typename Traits::VolumeVariables::PrimaryVariables;
130
131public:
133 using Problem = typename Traits::Problem;
134
136 using Indices = typename Traits::VolumeVariables::Indices;
137
139 using VolumeVariables = typename Traits::VolumeVariables;
140
142 static constexpr bool cachingEnabled = true;
143
145 using LocalView = typename Traits::template LocalView<ThisType, cachingEnabled>;
146
147 StaggeredGridVolumeVariables(const Problem& problem) : problemPtr_(&problem) {}
148
150 template<class GridGeometry, class SolutionVector>
151 void update(const GridGeometry& gridGeometry, const SolutionVector& sol)
152 {
153 if (sol.size() != gridGeometry.numScv())
154 DUNE_THROW(Dune::InvalidStateException, "The solution vector passed to the GridVolumeVariables has the wrong size.\n"
155 << "Make sure to initialize the gridVariables correctly: \n\n"
156 << "auto ffSol = partial(sol, ffFaceIdx, ffCellCenterIdx); \n"
157 << "ffGridVariables->init(ffSol);\n\n");
158
159 volumeVariables_.resize(gridGeometry.numScv());
160 auto fvGeometry = localView(gridGeometry);
161 for (const auto& element : elements(gridGeometry.gridView()))
162 {
163 fvGeometry.bindElement(element);
164 for (auto&& scv : scvs(fvGeometry))
165 {
166 // construct a privars object from the cell center solution vector
167 const auto& cellCenterPriVars = sol[scv.dofIndex()];
168 PrimaryVariables priVars = makePriVarsFromCellCenterPriVars<PrimaryVariables>(cellCenterPriVars);
169
170 auto elemSol = elementSolution<typename GridGeometry::LocalView>(std::move(priVars));
171 volumeVariables_[scv.dofIndex()].update(elemSol, problem(), element, scv);
172 }
173 }
174 }
175
176 const VolumeVariables& volVars(const std::size_t scvIdx) const
177 { return volumeVariables_[scvIdx]; }
178
179 VolumeVariables& volVars(const std::size_t scvIdx)
180 { return volumeVariables_[scvIdx]; }
181
182 template<class SubControlVolume, typename std::enable_if_t<!std::is_integral<SubControlVolume>::value, int> = 0>
183 const VolumeVariables& volVars(const SubControlVolume& scv) const
184 { return volumeVariables_[scv.dofIndex()]; }
185
186 template<class SubControlVolume, typename std::enable_if_t<!std::is_integral<SubControlVolume>::value, int> = 0>
187 VolumeVariables& volVars(const SubControlVolume& scv)
188 { return volumeVariables_[scv.dofIndex()]; }
189
190 const Problem& problem() const
191 { return *problemPtr_; }
192
195 template<class... Args>
196 PrimaryVariables getBoundaryPriVars(Args&&... args) const
197 {
198 return Traits::getBoundaryPriVars(std::forward<Args>(args)...);
199 }
200
201private:
202 const Problem* problemPtr_;
203 std::vector<VolumeVariables> volumeVariables_;
204};
205
206
212template<class Traits>
213class StaggeredGridVolumeVariables<Traits, /*cachingEnabled*/false>
214{
216 using PrimaryVariables = typename Traits::VolumeVariables::PrimaryVariables;
217
218public:
220 using Problem = typename Traits::Problem;
221
223 using VolumeVariables = typename Traits::VolumeVariables;
224
226 static constexpr bool cachingEnabled = false;
227
229 using LocalView = typename Traits::template LocalView<ThisType, cachingEnabled>;
230
231 StaggeredGridVolumeVariables(const Problem& problem) : problemPtr_(&problem) {}
232
233 template<class GridGeometry, class SolutionVector>
234 void update(const GridGeometry& gridGeometry, const SolutionVector& sol)
235 {
236 if (sol.size() != gridGeometry.numScv())
237 DUNE_THROW(Dune::InvalidStateException, "The solution vector passed to the GridVolumeVariables has the wrong size.\n"
238 << "Make sure to initialize the gridVariables correctly: \n\n"
239 << "auto ffSol = partial(sol, ffFaceIdx, ffCellCenterIdx); \n"
240 << "ffGridVariables->init(ffSol);\n\n");
241 }
242
243 const Problem& problem() const
244 { return *problemPtr_;}
245
248 template<class... Args>
249 PrimaryVariables getBoundaryPriVars(Args&&... args) const
250 {
251 return Traits::getBoundaryPriVars(std::forward<Args>(args)...);
252 }
253
254private:
255
256 const Problem* problemPtr_;
257};
258
259} // end namespace Dumux
260
261#endif
Base class for the element volume variables vector for the staggered model.
Definition: staggered/freeflow/elementvolumevariables.hh:32
Grid volume variables class for staggered models. Specialization in case of not storing the volume va...
Definition: staggered/freeflow/gridvolumevariables.hh:214
PrimaryVariables getBoundaryPriVars(Args &&... args) const
Definition: staggered/freeflow/gridvolumevariables.hh:249
void update(const GridGeometry &gridGeometry, const SolutionVector &sol)
Definition: staggered/freeflow/gridvolumevariables.hh:234
const Problem & problem() const
Definition: staggered/freeflow/gridvolumevariables.hh:243
typename Traits::VolumeVariables VolumeVariables
export the type of the VolumeVariables
Definition: staggered/freeflow/gridvolumevariables.hh:223
typename Traits::Problem Problem
export the problem type
Definition: staggered/freeflow/gridvolumevariables.hh:220
typename Traits::template LocalView< ThisType, cachingEnabled > LocalView
export the type of the local view
Definition: staggered/freeflow/gridvolumevariables.hh:229
StaggeredGridVolumeVariables(const Problem &problem)
Definition: staggered/freeflow/gridvolumevariables.hh:231
Grid volume variables class for staggered models. Specialization in case of storing the volume variab...
Definition: staggered/freeflow/gridvolumevariables.hh:127
typename Traits::VolumeVariables::Indices Indices
export the type of the indices
Definition: staggered/freeflow/gridvolumevariables.hh:136
typename Traits::Problem Problem
export the problem type
Definition: staggered/freeflow/gridvolumevariables.hh:133
const VolumeVariables & volVars(const SubControlVolume &scv) const
Definition: staggered/freeflow/gridvolumevariables.hh:183
typename Traits::template LocalView< ThisType, cachingEnabled > LocalView
export the type of the local view
Definition: staggered/freeflow/gridvolumevariables.hh:145
VolumeVariables & volVars(const SubControlVolume &scv)
Definition: staggered/freeflow/gridvolumevariables.hh:187
typename Traits::VolumeVariables VolumeVariables
export the type of the VolumeVariables
Definition: staggered/freeflow/gridvolumevariables.hh:139
VolumeVariables & volVars(const std::size_t scvIdx)
Definition: staggered/freeflow/gridvolumevariables.hh:179
void update(const GridGeometry &gridGeometry, const SolutionVector &sol)
Update all volume variables.
Definition: staggered/freeflow/gridvolumevariables.hh:151
const VolumeVariables & volVars(const std::size_t scvIdx) const
Definition: staggered/freeflow/gridvolumevariables.hh:176
const Problem & problem() const
Definition: staggered/freeflow/gridvolumevariables.hh:190
PrimaryVariables getBoundaryPriVars(Args &&... args) const
Definition: staggered/freeflow/gridvolumevariables.hh:196
StaggeredGridVolumeVariables(const Problem &problem)
Definition: staggered/freeflow/gridvolumevariables.hh:147
Grid volume variables class for staggered models.
Definition: staggered/freeflow/gridvolumevariables.hh:118
GridCache::LocalView localView(const GridCache &gridCache)
Free function to get the local view of a grid cache object.
Definition: localview.hh:26
Free function to get the local view of a grid cache object.
Definition: adapt.hh:17
The local element solution class for staggered methods.
Definition: staggered/freeflow/gridvolumevariables.hh:27
VV VolumeVariables
Definition: staggered/freeflow/gridvolumevariables.hh:29
P Problem
Definition: staggered/freeflow/gridvolumevariables.hh:28
static PrimaryVariables getBoundaryPriVars(const Problem &problem, const SolutionVector &sol, const Element &element, const SubControlVolumeFace &scvf)
Definition: staggered/freeflow/gridvolumevariables.hh:38
typename VV::PrimaryVariables PrimaryVariables
Definition: staggered/freeflow/gridvolumevariables.hh:30