OGS
RelPermBrooksCoreyNonwettingPhase.cpp
Go to the documentation of this file.
1// SPDX-FileCopyrightText: Copyright (c) OpenGeoSys Community (opengeosys.org)
2// SPDX-License-Identifier: BSD-3-Clause
3
5
6#include <algorithm>
7#include <cmath>
8
10
11namespace MaterialPropertyLib
12{
14 std::string name,
15 const double residual_liquid_saturation,
16 const double residual_gas_saturation,
17 const double min_relative_permeability,
18 const double exponent)
21 min_relative_permeability_(min_relative_permeability),
22 exponent_(exponent)
23{
24 name_ = std::move(name);
25};
26
28 VariableArray const& variable_array,
29 ParameterLib::SpatialPosition const& pos, double const t,
30 double const dt) const
31{
36 auto const s_L = std::visit(
37 [&variable_array, &pos, t, dt](auto&& scale) -> double
38 {
39 return scale->property(PropertyType::saturation)
40 .template value<double>(variable_array, pos, t, dt);
41 },
42 scale_);
43
44 auto const s_L_res = residual_liquid_saturation_;
45 auto const s_L_max = 1. - residual_gas_saturation_;
46
47 auto const lambda = exponent_;
48
49 auto const s_eff = (s_L - s_L_res) / (s_L_max - s_L_res);
50
51 if (s_eff >= 1.0)
52 {
53 // fully saturated medium
55 }
56 if (s_eff <= 0.0)
57 {
58 // dry medium
59 return 1.0;
60 }
61
62 auto const k_rel_GR = (1. - s_eff) * (1. - s_eff) *
63 (1. - std::pow(s_eff, (2. + lambda) / lambda));
64
65 return std::max(k_rel_GR, min_relative_permeability_);
66}
68 VariableArray const& variable_array, Variable const variable,
69 ParameterLib::SpatialPosition const& pos, double const t,
70 double const dt) const
71{
72 if (variable != Variable::liquid_saturation)
73 {
75 "RelPermBrooksCoreyNonwettingPhase::dValue is implemented for "
76 "derivatives with respect to liquid saturation only.");
77 }
82 auto const s_L = std::visit(
83 [&variable_array, &pos, t, dt](auto&& scale) -> double
84 {
85 return scale->property(PropertyType::saturation)
86 .template value<double>(variable_array, pos, t, dt);
87 },
88 scale_);
89
90 auto const s_L_res = residual_liquid_saturation_;
91 auto const s_L_max = 1. - residual_gas_saturation_;
92 auto const lambda = exponent_;
93
94 auto const s_eff = (s_L - s_L_res) / (s_L_max - s_L_res);
95 if ((s_eff < 0.) || (s_eff > 1.))
96 {
97 return 0.0;
98 }
99
100 auto const twoL_L = (2. + lambda) / lambda;
101 auto const d_se_d_sL = 1. / (s_L_max - s_L_res);
102 auto const dk_rel_GRdse =
103 -2. * (1 - s_eff) * (1. - std::pow(s_eff, twoL_L)) -
104 twoL_L * std::pow(s_eff, twoL_L - 1.) * (1. - s_eff) * (1. - s_eff);
105
106 return dk_rel_GRdse * d_se_d_sL;
107}
108
109} // namespace MaterialPropertyLib
#define OGS_FATAL(...)
Definition Error.h:19
virtual PropertyDataType value() const
std::variant< Medium *, Phase *, Component * > scale_
RelPermBrooksCoreyNonwettingPhase(std::string name, const double residual_liquid_saturation, const double residual_gas_saturation, const double min_relative_permeability, const double exponent)
PropertyDataType dValue(VariableArray const &variable_array, Variable const variable, ParameterLib::SpatialPosition const &pos, double const t, double const dt) const override
std::variant< double, Eigen::Matrix< double, 2, 1 >, Eigen::Matrix< double, 3, 1 >, Eigen::Matrix< double, 2, 2 >, Eigen::Matrix< double, 3, 3 >, Eigen::Matrix< double, 4, 1 >, Eigen::Matrix< double, 6, 1 >, Eigen::MatrixXd > PropertyDataType