version 3.8
porousmediumflow/richardsextended/volumevariables.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//
13#ifndef DUMUX_RICHARDSEXTENDED_VOLUME_VARIABLES_HH
14#define DUMUX_RICHARDSEXTENDED_VOLUME_VARIABLES_HH
15
16#include <cassert>
17
18#include <dune/common/exceptions.hh>
19
25
27
28namespace Dumux {
29
37template <class Traits>
40, public EnergyVolumeVariables<Traits, ExtendedRichardsVolumeVariables<Traits> >
41{
44 using Scalar = typename Traits::PrimaryVariables::value_type;
45 using PermeabilityType = typename Traits::PermeabilityType;
46 using ModelTraits = typename Traits::ModelTraits;
47
48 static constexpr int numFluidComps = ParentType::numFluidComponents();
49 static constexpr int numPhases = ParentType::numFluidPhases();
50
51 using EffDiffModel = typename Traits::EffectiveDiffusivityModel;
52
53 // checks if the fluid system uses the Richards model index convention
54 static constexpr auto fsCheck = ModelTraits::checkFluidSystem(typename Traits::FluidSystem{});
55
56public:
58 using FluidSystem = typename Traits::FluidSystem;
60 using FluidState = typename Traits::FluidState;
63 using SolidState = typename Traits::SolidState;
65 using SolidSystem = typename Traits::SolidSystem;
66 using Indices = typename Traits::ModelTraits::Indices;
68
70 static constexpr auto liquidPhaseIdx = Traits::FluidSystem::phase0Idx;
71 static constexpr auto gasPhaseIdx = Traits::FluidSystem::phase1Idx;
72
82 template<class ElemSol, class Problem, class Element, class Scv>
83 void update(const ElemSol &elemSol,
84 const Problem &problem,
85 const Element &element,
86 const Scv& scv)
87 {
88 ParentType::update(elemSol, problem, element, scv);
89
90 const auto fluidMatrixInteraction = problem.spatialParams().fluidMatrixInteraction(element, scv, elemSol);
91
92 const auto& priVars = elemSol[scv.localDofIndex()];
93 const auto phasePresence = priVars.state();
94
95 // precompute the minimum capillary pressure (entry pressure)
96 // needed to make sure we don't compute unphysical capillary pressures and thus saturations
97 minPc_ = fluidMatrixInteraction.endPointPc();
98
99 //update porosity before calculating the effective properties depending on it
100 updateSolidVolumeFractions(elemSol, problem, element, scv, solidState_, numFluidComps);
101
102 typename FluidSystem::ParameterCache paramCache;
103 auto getEffectiveDiffusionCoefficient = [&](int phaseIdx, int compIIdx, int compJIdx)
104 {
105 return EffDiffModel::effectiveDiffusionCoefficient(*this, phaseIdx, compIIdx, compJIdx);
106 };
107
108 if (phasePresence == Indices::gasPhaseOnly)
109 {
112 moleFraction_[gasPhaseIdx] = priVars[Indices::switchIdx];
113
114 const auto averageMolarMassGasPhase = (moleFraction_[gasPhaseIdx]*FluidSystem::molarMass(liquidPhaseIdx)) +
115 ((1-moleFraction_[gasPhaseIdx])*FluidSystem::molarMass(gasPhaseIdx));
116
117 //X_w = x_w* M_w/ M_avg
118 massFraction_[gasPhaseIdx] = priVars[Indices::switchIdx]*FluidSystem::molarMass(liquidPhaseIdx)/averageMolarMassGasPhase;
119
120 fluidState_.setSaturation(liquidPhaseIdx, 0.0);
121 fluidState_.setSaturation(gasPhaseIdx, 1.0);
122
123 EnergyVolVars::updateTemperature(elemSol, problem, element, scv, fluidState_, solidState_);
124
125 // get pc for sw = 0.0
126 const Scalar pc = fluidMatrixInteraction.pc(0.0);
127
128 // set the wetting pressure
129 fluidState_.setPressure(liquidPhaseIdx, problem.nonwettingReferencePressure() - pc);
130 fluidState_.setPressure(gasPhaseIdx, problem.nonwettingReferencePressure());
131
132 molarDensity_[liquidPhaseIdx] = FluidSystem::H2O::liquidDensity(temperature(), pressure(liquidPhaseIdx))/FluidSystem::H2O::molarMass();
133 molarDensity_[gasPhaseIdx] = IdealGas<Scalar>::molarDensity(temperature(), problem.nonwettingReferencePressure());
134
135 // density and viscosity
136 paramCache.updateAll(fluidState_);
140
141 // compute and set the enthalpy
142 fluidState_.setEnthalpy(liquidPhaseIdx, EnergyVolVars::enthalpy(fluidState_, paramCache, liquidPhaseIdx));
143 fluidState_.setEnthalpy(gasPhaseIdx, EnergyVolVars::enthalpy(fluidState_, paramCache, gasPhaseIdx));
144
145 //binary diffusion coefficients
146 paramCache.updateAll(fluidState_);
147 effectiveDiffCoeff_ = getEffectiveDiffusionCoefficient(gasPhaseIdx,
148 FluidSystem::comp1Idx,
149 FluidSystem::comp0Idx);
150 }
151 else if (phasePresence == Indices::bothPhases)
152 {
153 completeFluidState_(elemSol, problem, element, scv, fluidState_, solidState_);
154
155 // we want to account for diffusion in the air phase
156 // use Raoult to compute the water mole fraction in air
157 molarDensity_[liquidPhaseIdx] = FluidSystem::H2O::liquidDensity(temperature(), pressure(liquidPhaseIdx))/FluidSystem::H2O::molarMass();
158 molarDensity_[gasPhaseIdx] = IdealGas<Scalar>::molarDensity(temperature(), problem.nonwettingReferencePressure());
160
161 moleFraction_[gasPhaseIdx] = FluidSystem::H2O::vaporPressure(temperature()) / problem.nonwettingReferencePressure();
162
163 const auto averageMolarMassGasPhase = (moleFraction_[gasPhaseIdx]*FluidSystem::molarMass(liquidPhaseIdx)) +
164 ((1-moleFraction_[gasPhaseIdx])*FluidSystem::molarMass(gasPhaseIdx));
165
166 //X_w = x_w* M_w/ M_avg
167 massFraction_[gasPhaseIdx] = moleFraction_[gasPhaseIdx]*FluidSystem::molarMass(liquidPhaseIdx)/averageMolarMassGasPhase;
168
169 // binary diffusion coefficients
170 paramCache.updateAll(fluidState_);
171 effectiveDiffCoeff_ = getEffectiveDiffusionCoefficient(gasPhaseIdx,
172 FluidSystem::comp1Idx,
173 FluidSystem::comp0Idx);
174 }
175 else if (phasePresence == Indices::liquidPhaseOnly)
176 {
177 completeFluidState_(elemSol, problem, element, scv, fluidState_, solidState_);
178
179 molarDensity_[liquidPhaseIdx] = FluidSystem::H2O::liquidDensity(temperature(), pressure(liquidPhaseIdx))/FluidSystem::H2O::molarMass();
180 molarDensity_[gasPhaseIdx] = IdealGas<Scalar>::molarDensity(temperature(), problem.nonwettingReferencePressure());
185
186 // binary diffusion coefficients (none required for liquid phase only)
188 }
189
191 // specify the other parameters
193 relativePermeabilityWetting_ = fluidMatrixInteraction.krw(fluidState_.saturation(liquidPhaseIdx));
194 EnergyVolVars::updateSolidEnergyParams(elemSol, problem, element, scv, solidState_);
195 permeability_ = problem.spatialParams().permeability(element, scv, elemSol);
196 EnergyVolVars::updateEffectiveThermalConductivity();
197 }
198
203 const FluidState &fluidState() const
204 { return fluidState_; }
205
209 const SolidState &solidState() const
210 { return solidState_; }
211
215 Scalar temperature() const
216 { return fluidState_.temperature(); }
217
224 Scalar porosity() const
225 { return solidState_.porosity(); }
226
230 const PermeabilityType& permeability() const
231 { return permeability_; }
232
243 Scalar saturation(const int phaseIdx = liquidPhaseIdx) const
244 { return fluidState_.saturation(phaseIdx); }
245
252 Scalar density(const int phaseIdx = liquidPhaseIdx) const
253 { return fluidState_.density(phaseIdx); }
254
266 Scalar pressure(const int phaseIdx = liquidPhaseIdx) const
267 { return fluidState_.pressure(phaseIdx); }
268
280 Scalar mobility(const int phaseIdx = liquidPhaseIdx) const
281 { return relativePermeability(phaseIdx)/fluidState_.viscosity(phaseIdx); }
282
290 Scalar viscosity(const int phaseIdx = liquidPhaseIdx) const
291 { return phaseIdx == liquidPhaseIdx ? fluidState_.viscosity(liquidPhaseIdx) : 0.0; }
292
299 Scalar relativePermeability(const int phaseIdx = liquidPhaseIdx) const
300 { return phaseIdx == liquidPhaseIdx ? relativePermeabilityWetting_ : 1.0; }
301
313 Scalar capillaryPressure() const
314 {
315 using std::max;
317 }
318
333 Scalar pressureHead(const int phaseIdx = liquidPhaseIdx) const
334 { return 100.0 *(pressure(phaseIdx) - pressure(gasPhaseIdx))/density(phaseIdx)/9.81; }
335
346 Scalar waterContent(const int phaseIdx = liquidPhaseIdx) const
347 { return saturation(phaseIdx) * solidState_.porosity(); }
348
356 Scalar moleFraction(const int phaseIdx, const int compIdx) const
357 {
358 if (compIdx != FluidSystem::comp0Idx)
359 DUNE_THROW(Dune::InvalidStateException, "There is only one component for Richards!");
360 return moleFraction_[phaseIdx];
361 }
362
370 Scalar massFraction(const int phaseIdx, const int compIdx) const
371 {
372 if (compIdx != FluidSystem::comp0Idx)
373 DUNE_THROW(Dune::InvalidStateException, "There is only one component for Richards!");
374 return massFraction_[phaseIdx];
375 }
376
383 Scalar molarDensity(const int phaseIdx) const
384 {
385 return molarDensity_[phaseIdx];
386 }
387
391 Scalar diffusionCoefficient(int phaseIdx, int compIIdx, int compJIdx) const
392 {
393 assert(phaseIdx == gasPhaseIdx);
394 assert(compIIdx != compJIdx);
395 typename FluidSystem::ParameterCache paramCache;
396 paramCache.updatePhase(fluidState_, phaseIdx);
397 return FluidSystem::binaryDiffusionCoefficient(fluidState_, paramCache, phaseIdx, compIIdx, compJIdx);
398 }
399
403 Scalar effectiveDiffusionCoefficient(int phaseIdx, int compIIdx, int compJIdx) const
404 {
405 assert(phaseIdx == gasPhaseIdx);
406 assert(compIIdx != compJIdx);
407 return effectiveDiffCoeff_;
408 }
409private:
424 template<class ElemSol, class Problem, class Element, class Scv>
425 void completeFluidState_(const ElemSol& elemSol,
426 const Problem& problem,
427 const Element& element,
428 const Scv& scv,
431 {
432 EnergyVolVars::updateTemperature(elemSol, problem, element, scv, fluidState, solidState);
433
434 const auto fluidMatrixInteraction = problem.spatialParams().fluidMatrixInteraction(element, scv, elemSol);
435
436 const auto& priVars = elemSol[scv.localDofIndex()];
437
438 // set the wetting pressure
439 using std::max;
440 Scalar minPc = fluidMatrixInteraction.pc(1.0);
441 fluidState.setPressure(liquidPhaseIdx, priVars[Indices::pressureIdx]);
442 fluidState.setPressure(gasPhaseIdx, max(problem.nonwettingReferencePressure(), fluidState.pressure(liquidPhaseIdx) + minPc));
443
444 // compute the capillary pressure to compute the saturation
445 // make sure that we the capillary pressure is not smaller than the minimum pc
446 // this would possibly return unphysical values from regularized material laws
447 using std::max;
448 const Scalar pc = max(fluidMatrixInteraction.endPointPc(),
449 problem.nonwettingReferencePressure() - fluidState.pressure(liquidPhaseIdx));
450 const Scalar sw = fluidMatrixInteraction.sw(pc);
451 fluidState.setSaturation(liquidPhaseIdx, sw);
452 fluidState.setSaturation(gasPhaseIdx, 1.0-sw);
453
454 // density and viscosity
455 typename FluidSystem::ParameterCache paramCache;
456 paramCache.updateAll(fluidState);
457 fluidState.setDensity(liquidPhaseIdx,
459 fluidState.setDensity(gasPhaseIdx,
461
462 fluidState.setViscosity(liquidPhaseIdx,
464
465 // compute and set the enthalpy
466 fluidState.setEnthalpy(liquidPhaseIdx, EnergyVolVars::enthalpy(fluidState, paramCache, liquidPhaseIdx));
467 fluidState.setEnthalpy(gasPhaseIdx, EnergyVolVars::enthalpy(fluidState, paramCache, gasPhaseIdx));
468 }
469
470protected:
474 PermeabilityType permeability_;
475 Scalar minPc_;
476 Scalar moleFraction_[numPhases];
477 Scalar massFraction_[numPhases];
478 Scalar molarDensity_[numPhases];
479
480 // Effective diffusion coefficients for the phases
482
483};
484} // end namespace Dumux
485
486#endif
Definition: porousmediumflow/nonisothermal/volumevariables.hh:63
The primary variable switch controlling the phase presence state variable.
Definition: richardsextended/primaryvariableswitch.hh:29
Volume averaged quantities required by the extended Richards model.
Definition: porousmediumflow/richardsextended/volumevariables.hh:41
PermeabilityType permeability_
the intrinsic permeability
Definition: porousmediumflow/richardsextended/volumevariables.hh:474
const SolidState & solidState() const
Returns the phase state for the control volume.
Definition: porousmediumflow/richardsextended/volumevariables.hh:209
Scalar massFraction_[numPhases]
The water mass fractions in water and air.
Definition: porousmediumflow/richardsextended/volumevariables.hh:477
Scalar diffusionCoefficient(int phaseIdx, int compIIdx, int compJIdx) const
Returns the binary diffusion coefficients for a phase in .
Definition: porousmediumflow/richardsextended/volumevariables.hh:391
Scalar porosity() const
Returns the average porosity [] within the control volume.
Definition: porousmediumflow/richardsextended/volumevariables.hh:224
typename Traits::SolidState SolidState
Definition: porousmediumflow/richardsextended/volumevariables.hh:63
void update(const ElemSol &elemSol, const Problem &problem, const Element &element, const Scv &scv)
Updates all quantities for a given control volume.
Definition: porousmediumflow/richardsextended/volumevariables.hh:83
Scalar molarDensity_[numPhases]
The molar density of water and air.
Definition: porousmediumflow/richardsextended/volumevariables.hh:478
Scalar effectiveDiffCoeff_
Definition: porousmediumflow/richardsextended/volumevariables.hh:481
Scalar relativePermeabilityWetting_
the relative permeability of the wetting phase
Definition: porousmediumflow/richardsextended/volumevariables.hh:473
Scalar pressureHead(const int phaseIdx=liquidPhaseIdx) const
Returns the pressureHead of a given phase within the control volume.
Definition: porousmediumflow/richardsextended/volumevariables.hh:333
typename Traits::FluidState FluidState
Export type of the fluid state.
Definition: porousmediumflow/richardsextended/volumevariables.hh:60
Scalar viscosity(const int phaseIdx=liquidPhaseIdx) const
Returns the dynamic viscosity of a given phase within the control volume.
Definition: porousmediumflow/richardsextended/volumevariables.hh:290
Scalar effectiveDiffusionCoefficient(int phaseIdx, int compIIdx, int compJIdx) const
Returns the effective diffusion coefficients for a phase in .
Definition: porousmediumflow/richardsextended/volumevariables.hh:403
Scalar mobility(const int phaseIdx=liquidPhaseIdx) const
Returns the effective mobility of a given phase within the control volume.
Definition: porousmediumflow/richardsextended/volumevariables.hh:280
Scalar minPc_
the minimum capillary pressure (entry pressure)
Definition: porousmediumflow/richardsextended/volumevariables.hh:475
Scalar saturation(const int phaseIdx=liquidPhaseIdx) const
Returns the average absolute saturation [] of a given fluid phase within the finite volume.
Definition: porousmediumflow/richardsextended/volumevariables.hh:243
Scalar density(const int phaseIdx=liquidPhaseIdx) const
Returns the average mass density of a given fluid phase within the control volume.
Definition: porousmediumflow/richardsextended/volumevariables.hh:252
Scalar relativePermeability(const int phaseIdx=liquidPhaseIdx) const
Returns relative permeability [-] of a given phase within the control volume.
Definition: porousmediumflow/richardsextended/volumevariables.hh:299
typename Traits::ModelTraits::Indices Indices
Definition: porousmediumflow/richardsextended/volumevariables.hh:66
static constexpr auto gasPhaseIdx
Definition: porousmediumflow/richardsextended/volumevariables.hh:71
const PermeabilityType & permeability() const
Returns the permeability within the control volume in .
Definition: porousmediumflow/richardsextended/volumevariables.hh:230
Scalar capillaryPressure() const
Returns the effective capillary pressure within the control volume.
Definition: porousmediumflow/richardsextended/volumevariables.hh:313
Scalar moleFraction_[numPhases]
The water mole fractions in water and air.
Definition: porousmediumflow/richardsextended/volumevariables.hh:476
Scalar massFraction(const int phaseIdx, const int compIdx) const
Returns the mole fraction of a given component in a given phase within the control volume in .
Definition: porousmediumflow/richardsextended/volumevariables.hh:370
SolidState solidState_
Definition: porousmediumflow/richardsextended/volumevariables.hh:472
Scalar molarDensity(const int phaseIdx) const
Returns the mass density of a given phase within the control volume in .
Definition: porousmediumflow/richardsextended/volumevariables.hh:383
Scalar moleFraction(const int phaseIdx, const int compIdx) const
Returns the mole fraction of a given component in a given phase within the control volume in .
Definition: porousmediumflow/richardsextended/volumevariables.hh:356
typename Traits::FluidSystem FluidSystem
Export type of the fluid system.
Definition: porousmediumflow/richardsextended/volumevariables.hh:58
Scalar pressure(const int phaseIdx=liquidPhaseIdx) const
Returns the effective pressure of a given phase within the control volume.
Definition: porousmediumflow/richardsextended/volumevariables.hh:266
const FluidState & fluidState() const
Returns the fluid configuration at the given primary variables.
Definition: porousmediumflow/richardsextended/volumevariables.hh:203
Scalar waterContent(const int phaseIdx=liquidPhaseIdx) const
Returns the water content of a fluid phase within the finite volume.
Definition: porousmediumflow/richardsextended/volumevariables.hh:346
Scalar temperature() const
Returns the temperature.
Definition: porousmediumflow/richardsextended/volumevariables.hh:215
FluidState fluidState_
the fluid state
Definition: porousmediumflow/richardsextended/volumevariables.hh:471
typename Traits::SolidSystem SolidSystem
Export type of solid system.
Definition: porousmediumflow/richardsextended/volumevariables.hh:65
static constexpr auto liquidPhaseIdx
Export phase indices.
Definition: porousmediumflow/richardsextended/volumevariables.hh:70
static constexpr Scalar molarDensity(Scalar temperature, Scalar pressure)
The molar density of the gas , depending on pressure and temperature.
Definition: idealgas.hh:58
The isothermal base class.
Definition: porousmediumflow/volumevariables.hh:28
static constexpr int numFluidComponents()
Return number of components considered by the model.
Definition: porousmediumflow/volumevariables.hh:40
const PrimaryVariables & priVars() const
Returns the vector of primary variables.
Definition: porousmediumflow/volumevariables.hh:64
static constexpr int numFluidPhases()
Return number of phases considered by the model.
Definition: porousmediumflow/volumevariables.hh:38
void update(const ElemSol &elemSol, const Problem &problem, const Element &element, const Scv &scv)
Updates all quantities for a given control volume.
Definition: porousmediumflow/volumevariables.hh:52
A central place for various physical constants occurring in some equations.
void updateSolidVolumeFractions(const ElemSol &elemSol, const Problem &problem, const Element &element, const Scv &scv, SolidState &solidState, const int solidVolFracOffset)
update the solid volume fractions (inert and reacitve) and set them in the solidstate
Definition: updatesolidvolumefractions.hh:24
Relations valid for an ideal gas.
std::string phasePresence() noexcept
I/O name of phase presence.
Definition: name.hh:135
std::string viscosity(int phaseIdx) noexcept
I/O name of viscosity for multiphase systems.
Definition: name.hh:62
std::string density(int phaseIdx) noexcept
I/O name of density for multiphase systems.
Definition: name.hh:53
Definition: adapt.hh:17
Base class for the model specific class which provides access to all volume averaged quantities.
Base class for the model specific class which provides access to all volume averaged quantities.
The primary variable switch for the extended Richards model.
Update the solid volume fractions (inert and reacitve) and set them in the solidstate.