35 #include "../source/DUBValues.hpp"
36 #include "../source/DUB_FEM_handler.hpp"
37 #include "../source/assemble_DG.hpp"
38 #include "../source/face_handler_DG.hpp"
39 #include "../source/model_DG_t.hpp"
40 #include "../source/volume_handler_DG.hpp"
41 #include "source/core_model.hpp"
42 #include "source/geometry/mesh_handler.hpp"
43 #include "source/init.hpp"
44 #include "source/io/data_writer.hpp"
45 #include "source/numerics/bc_handler.hpp"
46 #include "source/numerics/linear_solver_handler.hpp"
47 #include "source/numerics/preconditioner_handler.hpp"
48 #include "source/numerics/tools.hpp"
62 : lifex::utils::FunctionDirichlet()
67 value(
const dealii::Point<lifex::dim> &p,
68 const unsigned int = 0)
const override
71 return std::sin(2 * M_PI * p[0]) * std::sin(2 * M_PI * p[1]) *
72 std::exp(-5 * this->get_time());
74 return std::sin(2 * M_PI * p[0] + M_PI / 4) *
75 std::sin(2 * M_PI * p[1] + M_PI / 4) *
76 std::sin(2 * M_PI * p[2] + M_PI / 4) *
77 std::exp(-5 * this->get_time());
89 : lifex::Function<lifex::dim>()
94 value(
const dealii::Point<lifex::dim> &p,
95 const unsigned int = 0)
const override
98 return std::sin(2 * M_PI * p[0]) * std::sin(2 * M_PI * p[1]) *
99 std::exp(-5 * this->get_time()) * (8 * M_PI * M_PI - 5);
101 return std::sin(2 * M_PI * p[0] + M_PI / 4) *
102 std::sin(2 * M_PI * p[1] + M_PI / 4) *
103 std::sin(2 * M_PI * p[2] + M_PI / 4) *
104 std::exp(-5 * this->get_time()) * (12 * M_PI * M_PI - 5);
116 : lifex::Function<lifex::dim>()
121 value(
const dealii::Point<lifex::dim> &p,
122 const unsigned int = 0)
const override
125 return -2 * M_PI * std::sin(2 * M_PI * p[0]) *
126 std::cos(2 * M_PI * p[1]) * std::exp(-5 * this->get_time()) *
127 (std::abs(p[1]) < 1e-10) +
128 2 * M_PI * std::cos(2 * M_PI * p[0]) *
129 std::sin(2 * M_PI * p[1]) * std::exp(-5 * this->get_time()) *
130 (std::abs(p[0] - 1) < 1e-10) +
131 2 * M_PI * std::sin(2 * M_PI * p[0]) *
132 std::cos(2 * M_PI * p[1]) * std::exp(-5 * this->get_time()) *
133 (std::abs(p[1] - 1) < 1e-10) -
134 2 * M_PI * std::cos(2 * M_PI * p[0]) *
135 std::sin(2 * M_PI * p[1]) * std::exp(-5 * this->get_time()) *
136 (std::abs(p[0]) < 1e-10);
138 return 2 * M_PI * std::cos(2 * M_PI * p[0] + M_PI / 4) *
139 std::sin(2 * M_PI * p[1] + M_PI / 4) *
140 std::sin(2 * M_PI * p[2] + M_PI / 4) *
141 std::exp(-5 * this->get_time()) *
142 (std::abs(p[0] - 1) < 1e-10) -
143 2 * M_PI * std::cos(2 * M_PI * p[0] + M_PI / 4) *
144 std::sin(2 * M_PI * p[1] + M_PI / 4) *
145 std::sin(2 * M_PI * p[2] + M_PI / 4) *
146 std::exp(-5 * this->get_time()) * (std::abs(p[0]) < 1e-10) +
147 2 * M_PI * std::sin(2 * M_PI * p[0] + M_PI / 4) *
148 std::cos(2 * M_PI * p[1] + M_PI / 4) *
149 std::sin(2 * M_PI * p[2] + M_PI / 4) *
150 std::exp(-5 * this->get_time()) *
151 (std::abs(p[1] - 1) < 1e-10) -
152 2 * M_PI * std::sin(2 * M_PI * p[0] + M_PI / 4) *
153 std::cos(2 * M_PI * p[1] + M_PI / 4) *
154 std::sin(2 * M_PI * p[2] + M_PI / 4) *
155 std::exp(-5 * this->get_time()) * (std::abs(p[1]) < 1e-10) +
156 2 * M_PI * std::sin(2 * M_PI * p[0] + M_PI / 4) *
157 std::sin(2 * M_PI * p[1] + M_PI / 4) *
158 std::cos(2 * M_PI * p[2] + M_PI / 4) *
159 std::exp(-5 * this->get_time()) *
160 (std::abs(p[2] - 1) < 1e-10) -
161 2 * M_PI * std::sin(2 * M_PI * p[0] + M_PI / 4) *
162 std::sin(2 * M_PI * p[1] + M_PI / 4) *
163 std::cos(2 * M_PI * p[2] + M_PI / 4) *
164 std::exp(-5 * this->get_time()) * (std::abs(p[2]) < 1e-10);
176 : lifex::Function<lifex::dim>()
181 value(
const dealii::Point<lifex::dim> &p,
182 const unsigned int component = 0)
const override
187 return 2 * M_PI * std::cos(2 * M_PI * p[0]) *
188 std::sin(2 * M_PI * p[1]) *
189 std::exp(-5 * this->get_time());
191 return 2 * M_PI * std::sin(2 * M_PI * p[0]) *
192 std::cos(2 * M_PI * p[1]) *
193 std::exp(-5 * this->get_time());
198 return 2 * M_PI * std::cos(2 * M_PI * p[0] + M_PI / 4) *
199 std::sin(2 * M_PI * p[1] + M_PI / 4) *
200 std::sin(2 * M_PI * p[2] + M_PI / 4) *
201 std::exp(-5 * this->get_time());
203 return 2 * M_PI * std::sin(2 * M_PI * p[0] + M_PI / 4) *
204 std::cos(2 * M_PI * p[1] + M_PI / 4) *
205 std::sin(2 * M_PI * p[2] + M_PI / 4) *
206 std::exp(-5 * this->get_time());
208 return 2 * M_PI * std::sin(2 * M_PI * p[0] + M_PI / 4) *
209 std::sin(2 * M_PI * p[1] + M_PI / 4) *
210 std::cos(2 * M_PI * p[2] + M_PI / 4) *
211 std::exp(-5 * this->get_time());
258 template <
class basis>
266 this->
u_ex = std::make_shared<heat_DG::ExactSolution>();
267 this->
grad_u_ex = std::make_shared<heat_DG::GradExactSolution>();
268 this->
f_ex = std::make_shared<heat_DG::RightHandSide>();
269 this->
g_n = std::make_shared<heat_DG::BCNeumann>();
278 template <
class basis>
292 dealii::FullMatrix<double> V(this->dofs_per_cell, this->dofs_per_cell);
294 dealii::FullMatrix<double> M(this->dofs_per_cell, this->dofs_per_cell);
296 dealii::FullMatrix<double> SC(this->dofs_per_cell, this->dofs_per_cell);
298 dealii::FullMatrix<double> IC(this->dofs_per_cell, this->dofs_per_cell);
300 dealii::FullMatrix<double> IC_t(this->dofs_per_cell, this->dofs_per_cell);
302 dealii::FullMatrix<double> IN(this->dofs_per_cell, this->dofs_per_cell);
304 dealii::FullMatrix<double> IN_t(this->dofs_per_cell, this->dofs_per_cell);
306 dealii::FullMatrix<double> SN(this->dofs_per_cell, this->dofs_per_cell);
309 dealii::Vector<double> cell_rhs(this->dofs_per_cell);
311 dealii::Vector<double> cell_rhs_edge(this->dofs_per_cell);
313 dealii::Vector<double> u0_rhs(this->dofs_per_cell);
315 std::vector<lifex::types::global_dof_index> dof_indices(
316 this->dofs_per_cell);
317 dealii::IndexSet owned_dofs = this->dof_handler.locally_owned_dofs();
318 const double &alpha_bdf = this->bdf_handler.get_alpha();
320 for (
const auto &cell : this->dof_handler.active_cell_iterators())
322 if (cell->is_locally_owned())
324 this->assemble->reinit(cell);
325 dof_indices = this->dof_handler.get_dof_indices(cell);
327 V = this->assemble->local_V();
328 M = this->assemble->local_M();
329 M /= this->prm_time_step;
332 cell_rhs = this->assemble->local_rhs(this->f_ex);
334 this->assemble->local_u0_M_rhs(this->solution_bdf, dof_indices);
335 u0_rhs /= this->prm_time_step;
337 this->matrix.add(dof_indices, V);
338 this->matrix.add(dof_indices, M);
339 this->rhs.add(dof_indices, cell_rhs);
340 this->rhs.add(dof_indices, u0_rhs);
342 for (
const auto &edge : cell->face_indices())
344 this->assemble->reinit(cell, edge);
345 std::vector<lifex::types::global_dof_index> dof_indices_neigh(
346 this->dofs_per_cell);
348 if (!cell->at_boundary(edge))
350 SC = this->assemble->local_SC(this->prm_stability_coeff);
352 this->assemble->local_IC(this->prm_penalty_coeff);
353 this->matrix.add(dof_indices, SC);
354 this->matrix.add(dof_indices, IC);
355 this->matrix.add(dof_indices, IC_t);
357 const auto neighcell = cell->neighbor(edge);
359 this->dof_handler.get_dof_indices(neighcell);
362 this->assemble->local_IN(this->prm_penalty_coeff);
363 SN = this->assemble->local_SN(this->prm_stability_coeff);
365 this->matrix.add(dof_indices, dof_indices_neigh, IN);
366 this->matrix.add(dof_indices_neigh, dof_indices, IN_t);
367 this->matrix.add(dof_indices, dof_indices_neigh, SN);
372 this->assemble->local_rhs_edge_neumann(this->g_n);
373 this->rhs.add(dof_indices, cell_rhs_edge);
379 this->matrix.compress(dealii::VectorOperation::add);
380 this->rhs.compress(dealii::VectorOperation::add);
Class to solve the heat equation using the Discontinuous Galerkin method.
void assemble_system() override
Assembly of the linear system.
Neumann boundary condition.
virtual double value(const dealii::Point< lifex::dim > &p, const unsigned int=0) const override
Evaluate the Neumann boundary condition function in a point.
Exact solution of the problem.
ExactSolution()
Constructor.
virtual double value(const dealii::Point< lifex::dim > &p, const unsigned int=0) const override
Evaluate the exact solution in a point.
Gradient of the exact solution.
GradExactSolution()
Constructor.
virtual double value(const dealii::Point< lifex::dim > &p, const unsigned int component=0) const override
Evaluate the gradient of the exact solution in a point.
RightHandSide()
Constructor.
virtual double value(const dealii::Point< lifex::dim > &p, const unsigned int=0) const override
Evaluate the source term in a point.
Class representing the resolution of time-dependent problems using discontinuous Galerkin methods.
std::shared_ptr< dealii::Function< lifex::dim > > g_n
Neumann boundary conditions.
std::shared_ptr< dealii::Function< lifex::dim > > f_ex
Known forcing term.
std::shared_ptr< dealii::Function< lifex::dim > > grad_u_ex
Pointer to exact gradient solution Function.
std::shared_ptr< lifex::utils::FunctionDirichlet > u_ex
Pointer to exact solution function.