OGS
HydroMechanicsFEM.h
Go to the documentation of this file.
1 
11 #pragma once
12 
13 #include <memory>
14 #include <vector>
15 
20 #include "MathLib/KelvinVector.h"
25 #include "ParameterLib/Parameter.h"
30 
31 namespace ProcessLib
32 {
33 namespace HydroMechanics
34 {
35 namespace MPL = MaterialPropertyLib;
36 
37 template <typename BMatricesType, typename ShapeMatricesTypeDisplacement,
38  typename ShapeMatricesTypePressure, int DisplacementDim, int NPoints>
40 {
46  solid_material.createMaterialStateVariables())
47  {
48  }
49 
50  typename ShapeMatricesTypeDisplacement::template MatrixType<
51  DisplacementDim, NPoints * DisplacementDim>
56 
57  typename ShapeMatricesTypeDisplacement::NodalRowVectorType N_u;
58  typename ShapeMatricesTypeDisplacement::GlobalDimNodalMatrixType dNdx_u;
59 
60  typename ShapeMatricesTypePressure::NodalRowVectorType N_p;
61  typename ShapeMatricesTypePressure::GlobalDimNodalMatrixType dNdx_p;
62 
64  std::unique_ptr<typename MaterialLib::Solids::MechanicsBase<
65  DisplacementDim>::MaterialStateVariables>
68 
69  // TODO disable in monolithic scheme to save memory
70  double coupling_pressure = std::numeric_limits<double>::quiet_NaN();
74  {
75  eps_prev = eps;
77  material_state_variables->pushBackState();
78  }
79 
82  double const t,
83  ParameterLib::SpatialPosition const& x_position,
84  double const dt,
85  double const temperature)
86  {
87  namespace MPL = MaterialPropertyLib;
88 
89  MPL::VariableArray variable_array;
90  MPL::VariableArray variable_array_prev;
91 
92  auto const null_state = solid_material.createMaterialStateVariables();
93 
95 
96  variable_array[static_cast<int>(MPL::Variable::stress)].emplace<KV>(
97  KV::Zero());
98  variable_array[static_cast<int>(MPL::Variable::mechanical_strain)]
99  .emplace<KV>(KV::Zero());
100  variable_array[static_cast<int>(MPL::Variable::temperature)]
101  .emplace<double>(temperature);
102 
103  variable_array_prev[static_cast<int>(MPL::Variable::stress)]
104  .emplace<KV>(KV::Zero());
105  variable_array_prev[static_cast<int>(MPL::Variable::mechanical_strain)]
106  .emplace<KV>(KV::Zero());
107  variable_array_prev[static_cast<int>(MPL::Variable::temperature)]
108  .emplace<double>(temperature);
109 
110  auto&& solution =
111  solid_material.integrateStress(variable_array_prev, variable_array,
112  t, x_position, dt, *null_state);
113 
114  if (!solution)
115  {
116  OGS_FATAL("Computation of elastic tangent stiffness failed.");
117  }
118 
120  std::move(std::get<2>(*solution));
121 
122  return C;
123  }
124 
125  template <typename DisplacementVectorType>
127  MPL::VariableArray const& variable_array,
128  double const t,
129  ParameterLib::SpatialPosition const& x_position,
130  double const dt,
131  DisplacementVectorType const& /*u*/,
132  double const T)
133  {
134  MaterialPropertyLib::VariableArray variable_array_prev;
135  variable_array_prev[static_cast<int>(
139  variable_array_prev[static_cast<int>(MaterialPropertyLib::Variable::
142  eps_prev);
143  variable_array_prev[static_cast<int>(
145  .emplace<double>(T);
146 
147  auto&& solution = solid_material.integrateStress(
148  variable_array_prev, variable_array, t, x_position, dt,
150 
151  if (!solution)
152  {
153  OGS_FATAL("Computation of local constitutive relation failed.");
154  }
155 
157  std::tie(sigma_eff, material_state_variables, C) = std::move(*solution);
158 
159  return C;
160  }
161 
163 };
164 
167 template <typename ShapeMatrixType>
169 {
170  std::vector<ShapeMatrixType, Eigen::aligned_allocator<ShapeMatrixType>> N_u;
171 };
172 
173 template <typename ShapeFunctionDisplacement, typename ShapeFunctionPressure,
174  typename IntegrationMethod, int DisplacementDim>
176  : public LocalAssemblerInterface<DisplacementDim>
177 {
178 public:
181 
182  // Types for pressure.
185 
186  static int const KelvinVectorSize =
189 
190  using SymmetricTensor = Eigen::Matrix<double, KelvinVectorSize, 1>;
191 
194 
196  MeshLib::Element const& e,
197  std::size_t const /*local_matrix_size*/,
198  bool const is_axially_symmetric,
199  unsigned const integration_order,
201 
203  std::size_t setIPDataInitialConditions(
204  std::string const& name,
205  double const* values,
206  int const integration_order) override;
207 
208  void assemble(double const /*t*/, double const /*dt*/,
209  std::vector<double> const& /*local_x*/,
210  std::vector<double> const& /*local_xdot*/,
211  std::vector<double>& /*local_M_data*/,
212  std::vector<double>& /*local_K_data*/,
213  std::vector<double>& /*local_rhs_data*/) override
214  {
215  OGS_FATAL(
216  "HydroMechanicsLocalAssembler: assembly without jacobian is not "
217  "implemented.");
218  }
219 
220  void assembleWithJacobian(double const t, double const dt,
221  std::vector<double> const& local_x,
222  std::vector<double> const& local_xdot,
223  const double /*dxdot_dx*/, const double /*dx_dx*/,
224  std::vector<double>& /*local_M_data*/,
225  std::vector<double>& /*local_K_data*/,
226  std::vector<double>& local_rhs_data,
227  std::vector<double>& local_Jac_data) override;
228 
230  const double t, double const dt, Eigen::VectorXd const& local_x,
231  Eigen::VectorXd const& local_xdot, const double dxdot_dx,
232  const double dx_dx, int const process_id,
233  std::vector<double>& local_M_data, std::vector<double>& local_K_data,
234  std::vector<double>& local_b_data,
235  std::vector<double>& local_Jac_data) override;
236 
237  void initializeConcrete() override
238  {
239  unsigned const n_integration_points =
240  _integration_method.getNumberOfPoints();
241 
242  for (unsigned ip = 0; ip < n_integration_points; ip++)
243  {
244  auto& ip_data = _ip_data[ip];
245 
247  if (_process_data.initial_stress != nullptr)
248  {
249  ParameterLib::SpatialPosition const x_position{
250  std::nullopt, _element.getID(), ip,
252  ShapeFunctionDisplacement,
254  _element, ip_data.N_u))};
255 
256  ip_data.sigma_eff =
258  DisplacementDim>((*_process_data.initial_stress)(
259  std::numeric_limits<
260  double>::quiet_NaN() /* time independent */,
261  x_position));
262  }
263 
264  ip_data.pushBackState();
265  }
266  }
267 
268  void postTimestepConcrete(Eigen::VectorXd const& /*local_x*/,
269  double const /*t*/,
270  double const /*dt*/) override
271  {
272  unsigned const n_integration_points =
273  _integration_method.getNumberOfPoints();
274 
275  for (unsigned ip = 0; ip < n_integration_points; ip++)
276  {
277  _ip_data[ip].pushBackState();
278  }
279  }
280 
282  double const t, double const dt, Eigen::VectorXd const& local_xs,
283  Eigen::VectorXd const& local_x_dot) override;
284 
285  void postNonLinearSolverConcrete(std::vector<double> const& local_x,
286  std::vector<double> const& local_xdot,
287  double const t, double const dt,
288  bool const use_monolithic_scheme,
289  int const process_id) override;
290 
291  void setInitialConditionsConcrete(std::vector<double> const& local_x,
292  double const t,
293  bool const use_monolithic_scheme,
294  int const process_id) override;
295 
296  Eigen::Map<const Eigen::RowVectorXd> getShapeMatrix(
297  const unsigned integration_point) const override
298  {
299  auto const& N_u = _secondary_data.N_u[integration_point];
300 
301  // assumes N is stored contiguously in memory
302  return Eigen::Map<const Eigen::RowVectorXd>(N_u.data(), N_u.size());
303  }
304 
305  // TODO (naumov) This method is same as getIntPtSigma but for arguments and
306  // the ordering of the cache_mat.
307  // There should be only one.
308  std::vector<double> getSigma() const override;
309 
310  std::vector<double> getEpsilon() const override;
311 
312  std::vector<double> const& getIntPtDarcyVelocity(
313  const double t,
314  std::vector<GlobalVector*> const& x,
315  std::vector<NumLib::LocalToGlobalIndexMap const*> const& dof_table,
316  std::vector<double>& cache) const override;
317 
318  std::vector<double> const& getIntPtSigma(
319  const double /*t*/,
320  std::vector<GlobalVector*> const& /*x*/,
321  std::vector<NumLib::LocalToGlobalIndexMap const*> const& /*dof_table*/,
322  std::vector<double>& cache) const override
323  {
324  return ProcessLib::getIntegrationPointKelvinVectorData<DisplacementDim>(
325  _ip_data, &IpData::sigma_eff, cache);
326  }
327 
328  std::vector<double> const& getIntPtEpsilon(
329  const double /*t*/,
330  std::vector<GlobalVector*> const& /*x*/,
331  std::vector<NumLib::LocalToGlobalIndexMap const*> const& /*dof_table*/,
332  std::vector<double>& cache) const override
333  {
334  return ProcessLib::getIntegrationPointKelvinVectorData<DisplacementDim>(
335  _ip_data, &IpData::eps, cache);
336  }
337 
338 private:
358  const double t, double const dt, Eigen::VectorXd const& local_x,
359  std::vector<double>& local_b_data, std::vector<double>& local_Jac_data);
360 
385  const double t, double const dt, Eigen::VectorXd const& local_x,
386  Eigen::VectorXd const& local_xdot, std::vector<double>& local_b_data,
387  std::vector<double>& local_Jac_data);
388 
389  unsigned getNumberOfIntegrationPoints() const override;
390 
392  DisplacementDim>::MaterialStateVariables const&
393  getMaterialStateVariablesAt(unsigned integration_point) const override;
394 
395 private:
397 
400  using IpData =
402  ShapeMatricesTypePressure, DisplacementDim,
403  ShapeFunctionDisplacement::NPOINTS>;
404  std::vector<IpData, Eigen::aligned_allocator<IpData>> _ip_data;
405 
406  IntegrationMethod _integration_method;
412 
413  static const int pressure_index = 0;
414  static const int pressure_size = ShapeFunctionPressure::NPOINTS;
415  static const int displacement_index = ShapeFunctionPressure::NPOINTS;
416  static const int displacement_size =
417  ShapeFunctionDisplacement::NPOINTS * DisplacementDim;
418 };
419 
420 } // namespace HydroMechanics
421 } // namespace ProcessLib
422 
423 #include "HydroMechanicsFEM-impl.h"
#define OGS_FATAL(...)
Definition: Error.h:26
virtual std::size_t getID() const final
Returns the ID of the element.
Definition: Element.h:82
void postNonLinearSolverConcrete(std::vector< double > const &local_x, std::vector< double > const &local_xdot, double const t, double const dt, bool const use_monolithic_scheme, int const process_id) override
void computeSecondaryVariableConcrete(double const t, double const dt, Eigen::VectorXd const &local_xs, Eigen::VectorXd const &local_x_dot) override
Eigen::Map< const Eigen::RowVectorXd > getShapeMatrix(const unsigned integration_point) const override
Provides the shape matrix at the given integration point.
void postTimestepConcrete(Eigen::VectorXd const &, double const, double const) override
HydroMechanicsProcessData< DisplacementDim > & _process_data
HydroMechanicsLocalAssembler(HydroMechanicsLocalAssembler &&)=delete
void assembleWithJacobianForDeformationEquations(const double t, double const dt, Eigen::VectorXd const &local_x, std::vector< double > &local_b_data, std::vector< double > &local_Jac_data)
std::vector< IpData, Eigen::aligned_allocator< IpData > > _ip_data
ShapeMatrixPolicyType< ShapeFunctionPressure, DisplacementDim > ShapeMatricesTypePressure
Eigen::Matrix< double, KelvinVectorSize, 1 > SymmetricTensor
std::size_t setIPDataInitialConditions(std::string const &name, double const *values, int const integration_order) override
Returns number of read integration points.
std::vector< double > const & getIntPtEpsilon(const double, std::vector< GlobalVector * > const &, std::vector< NumLib::LocalToGlobalIndexMap const * > const &, std::vector< double > &cache) const override
void assembleWithJacobianForStaggeredScheme(const double t, double const dt, Eigen::VectorXd const &local_x, Eigen::VectorXd const &local_xdot, const double dxdot_dx, const double dx_dx, int const process_id, std::vector< double > &local_M_data, std::vector< double > &local_K_data, std::vector< double > &local_b_data, std::vector< double > &local_Jac_data) override
BMatrixPolicyType< ShapeFunctionDisplacement, DisplacementDim > BMatricesType
void assembleWithJacobianForPressureEquations(const double t, double const dt, Eigen::VectorXd const &local_x, Eigen::VectorXd const &local_xdot, std::vector< double > &local_b_data, std::vector< double > &local_Jac_data)
SecondaryData< typename ShapeMatricesTypeDisplacement::ShapeMatrices::ShapeType > _secondary_data
HydroMechanicsLocalAssembler(HydroMechanicsLocalAssembler const &)=delete
void assembleWithJacobian(double const t, double const dt, std::vector< double > const &local_x, std::vector< double > const &local_xdot, const double, const double, std::vector< double > &, std::vector< double > &, std::vector< double > &local_rhs_data, std::vector< double > &local_Jac_data) override
ShapeMatrixPolicyType< ShapeFunctionDisplacement, DisplacementDim > ShapeMatricesTypeDisplacement
std::vector< double > const & getIntPtSigma(const double, std::vector< GlobalVector * > const &, std::vector< NumLib::LocalToGlobalIndexMap const * > const &, std::vector< double > &cache) const override
void setInitialConditionsConcrete(std::vector< double > const &local_x, double const t, bool const use_monolithic_scheme, int const process_id) override
void assemble(double const, double const, std::vector< double > const &, std::vector< double > const &, std::vector< double > &, std::vector< double > &, std::vector< double > &) override
std::vector< double > const & getIntPtDarcyVelocity(const double t, std::vector< GlobalVector * > const &x, std::vector< NumLib::LocalToGlobalIndexMap const * > const &dof_table, std::vector< double > &cache) const override
MaterialLib::Solids::MechanicsBase< DisplacementDim >::MaterialStateVariables const & getMaterialStateVariablesAt(unsigned integration_point) const override
std::array< VariableType, static_cast< int >(Variable::number_of_variables)> VariableArray
Definition: VariableType.h:108
Eigen::Matrix< double, kelvin_vector_dimensions(DisplacementDim), 1, Eigen::ColMajor > KelvinVectorType
Definition: KelvinVector.h:48
constexpr int kelvin_vector_dimensions(int const displacement_dim)
Kelvin vector dimensions for given displacement dimension.
Definition: KelvinVector.h:23
Eigen::Matrix< double, kelvin_vector_dimensions(DisplacementDim), kelvin_vector_dimensions(DisplacementDim), Eigen::RowMajor > KelvinMatrixType
Definition: KelvinVector.h:56
Eigen::Matrix< double, Eigen::MatrixBase< Derived >::RowsAtCompileTime, 1 > symmetricTensorToKelvinVector(Eigen::MatrixBase< Derived > const &v)
Definition: KelvinVector.h:170
MathLib::TemplatePoint< double, 3 > Point3d
std::array< double, 3 > interpolateCoordinates(MeshLib::Element const &e, typename ShapeMatricesType::ShapeMatrices::ShapeType const &N)
BMatricesType::KelvinMatrixType updateConstitutiveRelation(MPL::VariableArray const &variable_array, double const t, ParameterLib::SpatialPosition const &x_position, double const dt, DisplacementVectorType const &, double const T)
ShapeMatricesTypeDisplacement::GlobalDimNodalMatrixType dNdx_u
std::unique_ptr< typename MaterialLib::Solids::MechanicsBase< DisplacementDim >::MaterialStateVariables > material_state_variables
ShapeMatricesTypeDisplacement::NodalRowVectorType N_u
ShapeMatricesTypeDisplacement::template MatrixType< DisplacementDim, NPoints *DisplacementDim > N_u_op
ShapeMatricesTypePressure::GlobalDimNodalMatrixType dNdx_p
MathLib::KelvinVector::KelvinMatrixType< DisplacementDim > computeElasticTangentStiffness(double const t, ParameterLib::SpatialPosition const &x_position, double const dt, double const temperature)
ShapeMatricesTypePressure::NodalRowVectorType N_p
BMatricesType::KelvinVectorType sigma_eff_prev
MaterialLib::Solids::MechanicsBase< DisplacementDim > const & solid_material
IntegrationPointData(MaterialLib::Solids::MechanicsBase< DisplacementDim > const &solid_material)
std::vector< ShapeMatrixType, Eigen::aligned_allocator< ShapeMatrixType > > N_u