OGS
SaturationDependentSwelling.cpp
Go to the documentation of this file.
1
11
12#include <cmath>
13
17
18namespace MaterialPropertyLib
19{
21 std::string name,
22 std::array<double, 3>
23 swelling_pressures,
24 std::array<double, 3>
25 exponents,
26 double const lower_saturation_limit,
27 double const upper_saturation_limit,
28 ParameterLib::CoordinateSystem const* const local_coordinate_system)
29 : p_(std::move(swelling_pressures)),
30 lambda_(std::move(exponents)),
31 S_min_(lower_saturation_limit),
32 S_max_(upper_saturation_limit),
33 local_coordinate_system_(local_coordinate_system)
34{
35 name_ = std::move(name);
36}
37
39{
40 if (!std::holds_alternative<Phase*>(scale_))
41 {
43 "The property 'SaturationDependentSwelling' is implemented on the "
44 "'phase' scales only.");
45 }
46 auto const phase = std::get<Phase*>(scale_);
47 if (phase->name != "Solid")
48 {
50 "The property 'SaturationDependentSwelling' must be given in the "
51 "'Solid' phase, not in '{:s}' phase.",
52 phase->name);
53 }
54}
55
57 VariableArray const& variable_array,
58 VariableArray const& variable_array_prev,
59 ParameterLib::SpatialPosition const& pos, double const /*t*/,
60 double const dt) const
61{
62 auto const S_L = variable_array.liquid_saturation;
63 auto const S_L_prev = variable_array_prev.liquid_saturation;
64
65 Eigen::Matrix<double, 3, 3> const e =
67 ? Eigen::Matrix<double, 3, 3>::Identity()
69
70 Eigen::Matrix<double, 3, 3> delta_sigma_sw =
71 Eigen::Matrix<double, 3, 3>::Zero();
72
73 if (S_L < S_min_)
74 {
75 return delta_sigma_sw; // still being zero.
76 }
77
78 double const S_eff = std::clamp((S_L - S_min_) / (S_max_ - S_min_), 0., 1.);
79 double const S_eff_prev =
80 std::clamp((S_L_prev - S_min_) / (S_max_ - S_min_), 0., 1.);
81
82 double const delta_S_eff = S_eff - S_eff_prev;
83
84 if (delta_S_eff == 0.)
85 {
86 return delta_sigma_sw; // still being zero.
87 }
88
89 // \Delta\sigma_{sw} = - \sum_i k_i (\lambda p S_{eff}^{(\lambda_i - 1)}
90 // e_i \otimes e_i \Delta S_L / (S_{max} - S_{min}), where
91 // e_i \otimes e_i is a square matrix with e_i,0^2 e_i,0*e_i,1 etc.
92 for (int i = 0; i < 3; ++i)
93 {
94 Eigen::Matrix<double, 3, 3> const ei_otimes_ei =
95 e.col(i) * e.col(i).transpose();
96
97 delta_sigma_sw -=
98 lambda_[i] * p_[i] * std::pow(S_eff, lambda_[i] - 1) * ei_otimes_ei;
99 }
100
101 return (delta_sigma_sw * delta_S_eff / dt).eval();
102}
103
105 VariableArray const& variable_array,
106 VariableArray const& variable_array_prev, Variable const variable,
107 ParameterLib::SpatialPosition const& pos, double const /*t*/,
108 double const /*dt*/) const
109{
110 if (variable != Variable::liquid_saturation)
111 {
112 OGS_FATAL(
113 "SaturationDependentSwelling::dValue is implemented for "
114 "derivatives with respect to liquid saturation only.");
115 }
116
117 auto const S_L = variable_array.liquid_saturation;
118 auto const S_L_prev = variable_array_prev.liquid_saturation;
119
120 Eigen::Matrix<double, 3, 3> const e =
121 local_coordinate_system_ == nullptr
122 ? Eigen::Matrix<double, 3, 3>::Identity()
124
125 Eigen::Matrix<double, 3, 3> delta_sigma_sw =
126 Eigen::Matrix<double, 3, 3>::Zero();
127
128 if (S_L < S_min_)
129 {
130 return delta_sigma_sw; // still being zero.
131 }
132
133 double const S_eff = std::clamp((S_L - S_min_) / (S_max_ - S_min_), 0., 1.);
134 double const S_eff_prev =
135 std::clamp((S_L_prev - S_min_) / (S_max_ - S_min_), 0., 1.);
136
137 double const delta_S_eff = S_eff - S_eff_prev;
138
139 // Heaviside(delta S_eff,sw)
140 if (std::abs(delta_S_eff) <= 0)
141 {
142 return delta_sigma_sw; // still being zero.
143 }
144
145 for (int i = 0; i < 3; ++i)
146 {
147 Eigen::Matrix<double, 3, 3> const ei_otimes_ei =
148 e.col(i) * e.col(i).transpose();
149
150 delta_sigma_sw +=
151 lambda_[i] * p_[i] * std::pow(S_eff, lambda_[i] - 1) * ei_otimes_ei;
152 }
153 return (delta_sigma_sw / (S_max_ - S_min_)).eval();
154}
155} // namespace MaterialPropertyLib
#define OGS_FATAL(...)
Definition Error.h:26
virtual PropertyDataType value() const
Definition Property.cpp:76
std::variant< Medium *, Phase *, Component * > scale_
Definition Property.h:297
std::array< double, 3 > const p_
Maximum swelling pressures, one for each spatial dimension.
PropertyDataType dValue(VariableArray const &variable_array, VariableArray const &variable_array_prev, Variable const variable, ParameterLib::SpatialPosition const &pos, double const t, double const dt) const override
ParameterLib::CoordinateSystem const *const local_coordinate_system_
SaturationDependentSwelling(std::string name, std::array< double, 3 > swelling_pressures, std::array< double, 3 > exponents, double const lower_saturation_limit, double const upper_saturation_limit, ParameterLib::CoordinateSystem const *const local_coordinate_system)
std::array< double, 3 > const lambda_
Exponents, one for each spatial dimension.
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
Definition Property.h:31
A local coordinate system used for tensor transformations.
Eigen::Matrix< double, 3, 3 > transformation_3d(SpatialPosition const &pos) const