31 #include "libmesh/string_to_enum.h" 34 #include "libmesh/enum_solver_package.h" 37 #include "libmesh/mesh.h" 38 #include "libmesh/mesh_generation.h" 39 #include "libmesh/mesh_modification.h" 42 #include "libmesh/dense_matrix.h" 43 #include "libmesh/sparse_matrix.h" 44 #include "libmesh/dense_vector.h" 45 #include "libmesh/numeric_vector.h" 48 #include "libmesh/fe.h" 49 #include "libmesh/elem.h" 52 #include "libmesh/quadrature_gauss.h" 55 #include "libmesh/dof_map.h" 58 #include "libmesh/equation_systems.h" 59 #include "libmesh/linear_implicit_system.h" 62 #include "libmesh/exact_solution.h" 63 #include "libmesh/enum_norm_type.h" 64 #include "solution_function.h" 67 #include "libmesh/getpot.h" 68 #include "libmesh/exodusII_io.h" 81 const std::string & system_name);
83 int main (
int argc,
char ** argv)
90 "--enable-petsc, --enable-trilinos, or --enable-eigen");
93 GetPot infile(
"vector_fe_ex6.in");
96 infile.parse_command_line(argc, argv);
99 const unsigned int dimension = infile(
"dim", 2);
100 const unsigned int grid_size = infile(
"grid_size", 15);
103 libmesh_example_requires(dimension <= LIBMESH_DIM, dimension <<
"D support");
112 const std::string elem_str = infile(
"element_type", std::string(
"TRI6"));
114 libmesh_error_msg_if((dimension == 2 && elem_str !=
"TRI6" && elem_str !=
"TRI7" && elem_str !=
"QUAD8" && elem_str !=
"QUAD9") ||
115 (dimension == 3 && elem_str !=
"TET14" && elem_str !=
"HEX27"),
116 "You selected " << elem_str <<
117 " but this example must be run with TRI6, TRI7, QUAD8, or QUAD9 in 2d" <<
118 " or with TET14, or HEX27 in 3d.");
120 const std::string bc_str = infile(
"boundary_condition", std::string(
"neumann"));
121 libmesh_error_msg_if(
122 (bc_str !=
"neumann") && (bc_str !=
"dirichlet"),
123 "You selected '" << bc_str <<
"', however, the valid options are 'dirichlet' or 'neumann'");
124 const bool neumann = (bc_str ==
"neumann");
132 Utility::string_to_enum<ElemType>(elem_str));
133 else if (dimension == 3)
141 Utility::string_to_enum<ElemType>(elem_str));
157 const Order vector_order =
static_cast<Order>(infile(
"order", 1u));
158 const Order scalar_order =
static_cast<Order>(vector_order - 1u);
160 libmesh_error_msg_if(vector_order < FIRST || vector_order > ((dimension == 3) ?
FIRST :
FIFTH),
161 "You selected: " << vector_order <<
162 " but this example must be run with either 1 <= order <= 5 in 2d" 163 " or with order 1 in 3d.");
179 equation_systems.
init();
197 std::vector<FunctionBase<Number> *> sols(1, &soln_func);
198 std::vector<FunctionBase<Gradient> *> grads(1, &soln_grad);
203 else if (dimension == 3)
209 std::vector<FunctionBase<Number> *> sols(1, &soln_func);
210 std::vector<FunctionBase<Gradient> *> grads(1, &soln_grad);
217 int extra_error_quadrature = infile(
"extra_error_quadrature", 2);
228 << exact_sol.
l2_error(
"DivGrad",
"u")
239 << exact_sol.
l2_error(
"DivGrad",
"p")
242 #ifdef LIBMESH_HAVE_EXODUS_API 247 #endif // #ifdef LIBMESH_HAVE_EXODUS_API 261 const std::string & libmesh_dbg_var(system_name))
266 libmesh_assert_equal_to (system_name,
"DivGrad");
303 vector_fe->attach_quadrature_rule (&qrule);
304 scalar_fe->attach_quadrature_rule (&qrule);
314 vector_fe_face->attach_quadrature_rule (&qface);
320 const std::vector<Real> & JxW = vector_fe->get_JxW();
325 const std::vector<Point> & q_point = vector_fe->get_xyz();
328 const std::vector<std::vector<RealGradient>> & vector_phi = vector_fe->get_phi();
329 const std::vector<std::vector<Real>> & scalar_phi = scalar_fe->get_phi();
333 const std::vector<std::vector<Real>> & div_vector_phi = vector_fe->get_div_phi();
347 std::vector<dof_id_type> dof_indices;
348 std::vector<dof_id_type> vector_dof_indices;
349 std::vector<dof_id_type> scalar_dof_indices;
350 std::vector<dof_id_type> lambda_dof_indices;
368 for (
const auto & elem :
mesh.active_local_element_ptr_range())
374 dof_map.dof_indices (elem, dof_indices);
375 dof_map.dof_indices (elem, vector_dof_indices, system.
variable_number(
"u"));
376 dof_map.dof_indices (elem, scalar_dof_indices, system.
variable_number(
"p"));
378 dof_map.dof_indices (elem, lambda_dof_indices, system.
variable_number(
"l"));
385 const unsigned int n_dofs =
386 cast_int<unsigned int>(dof_indices.size());
387 const unsigned int vector_n_dofs =
388 cast_int<unsigned int>(vector_dof_indices.size());
389 const unsigned int scalar_n_dofs =
390 cast_int<unsigned int>(scalar_dof_indices.size());
391 const unsigned int lambda_n_dofs =
392 cast_int<unsigned int>(lambda_dof_indices.size());
398 vector_fe->reinit (elem);
399 scalar_fe->reinit (elem);
404 libmesh_assert_equal_to (n_dofs, vector_n_dofs + scalar_n_dofs + lambda_n_dofs);
405 libmesh_assert_equal_to (vector_n_dofs, vector_phi.size());
406 libmesh_assert_equal_to (scalar_n_dofs, scalar_phi.size());
417 Ke.
resize (n_dofs, n_dofs);
422 for (
unsigned int qp=0; qp<qrule.n_points(); qp++)
428 for (
unsigned int i = 0; i != vector_n_dofs; i++)
429 for (
unsigned int j = 0; j != vector_n_dofs; j++)
431 Ke(i, j) += JxW[qp]*(vector_phi[i][qp]*vector_phi[j][qp]);
437 for (
unsigned int i = 0; i != vector_n_dofs; i++)
438 for (
unsigned int l = 0; l != scalar_n_dofs; l++)
440 Ke(i, l + vector_n_dofs) -= JxW[qp]*(div_vector_phi[i][qp]*scalar_phi[l][qp]);
446 for (
unsigned int k = 0; k != scalar_n_dofs; k++)
447 for (
unsigned int j = 0; j != vector_n_dofs; j++)
449 Ke(k + vector_n_dofs, j) -= JxW[qp]*(div_vector_phi[j][qp]*scalar_phi[k][qp]);
458 const Real x = q_point[qp](0);
459 const Real y = q_point[qp](1);
460 const Real z = q_point[qp](2);
473 for (
unsigned int k = 0; k != scalar_n_dofs; k++)
475 Fe(k + vector_n_dofs) -= JxW[qp]*f*scalar_phi[k][qp];
486 const Real x = q_point[qp](0);
487 const Real y = q_point[qp](1);
488 const Real z = q_point[qp](2);
491 Real scalar_value = 0;
499 for (
unsigned int k = 0; k != scalar_n_dofs; k++)
500 for (
unsigned int n = 0; n != lambda_n_dofs; n++)
502 Ke(k + vector_n_dofs, n + vector_n_dofs + scalar_n_dofs) += JxW[qp]*scalar_phi[k][qp];
507 for (
unsigned int m = 0; m != lambda_n_dofs; m++)
508 for (
unsigned int l = 0; l != scalar_n_dofs; l++)
510 Ke(m + vector_n_dofs + scalar_n_dofs, l + vector_n_dofs) += JxW[qp]*scalar_phi[l][qp];
514 for (
unsigned int m = 0; m != lambda_n_dofs; m++)
516 Fe(m + vector_n_dofs + scalar_n_dofs) += JxW[qp]*scalar_value;
533 for (
auto side : elem->side_index_range())
534 if (elem->neighbor_ptr(side) ==
nullptr)
537 const std::vector<std::vector<RealGradient>> & vector_phi_face = vector_fe_face->get_phi();
541 const std::vector<Real> & JxW_face = vector_fe_face->get_JxW();
546 const std::vector<Point> & qface_point = vector_fe_face->get_xyz();
547 const std::vector<Point> & normals = vector_fe_face->get_normals();
550 vector_fe_face->reinit(elem, side);
554 libmesh_assert_equal_to (vector_n_dofs, vector_phi_face.size());
557 for (
unsigned int qp=0; qp<qface.n_points(); qp++)
561 const Real xf = qface_point[qp](0);
562 const Real yf = qface_point[qp](1);
563 const Real zf = qface_point[qp](2);
576 const Real penalty = 1.e10;
581 for (
unsigned int i = 0; i != vector_n_dofs; i++)
582 for (
unsigned int j = 0; j != vector_n_dofs; j++)
584 Ke(i, j) += JxW_face[qp]*penalty*vector_phi_face[i][qp]*
585 normals[qp]*vector_phi_face[j][qp]*normals[qp];
591 for (
unsigned int i = 0; i != vector_n_dofs; i++)
593 Fe(i) += JxW_face[qp]*penalty*vector_phi_face[i][qp]*normals[qp]*
594 vector_value*normals[qp];
600 Real scalar_value = 0;
608 for (
unsigned int i = 0; i != vector_n_dofs; i++)
610 Fe(i) += -JxW_face[qp]*vector_phi_face[i][qp]*normals[qp]*scalar_value;
622 dof_map.constrain_element_matrix_and_vector (Ke, Fe, dof_indices);
class FEType hides (possibly multiple) FEFamily and approximation orders, thereby enabling specialize...
This class handles the computation of the L2 and/or H1 error for the Systems in the EquationSystems o...
void assemble_divgrad(EquationSystems &es, const std::string &system_name)
This is the EquationSystems class.
Order
defines an enum for polynomial orders.
Real hdiv_error(std::string_view sys_name, std::string_view unknown_name)
The ExodusII_IO class implements reading meshes in the ExodusII file format from Sandia National Labs...
void attach_exact_values(const std::vector< FunctionBase< Number > *> &f)
Clone and attach arbitrary functors which compute the exact values of the EquationSystems' solutions ...
Manages consistently variables, degrees of freedom, coefficient vectors, matrices and linear solvers ...
void resize(const unsigned int n)
Resize the vector.
virtual void add_vector(const T *v, const std::vector< numeric_index_type > &dof_indices)
Computes , where v is a pointer and each dof_indices[i] specifies where to add value v[i]...
void print_info(std::ostream &os=libMesh::out) const
Prints information about the equation systems, by default to libMesh::out.
void extra_quadrature_order(const int extraorder)
Increases or decreases the order of the quadrature rule used for numerical integration.
NumericVector< Number > * rhs
The system matrix.
Order default_quadrature_order() const
The LibMeshInit class, when constructed, initializes the dependent libraries (e.g.
The libMesh namespace provides an interface to certain functionality in the library.
void attach_exact_derivs(const std::vector< FunctionBase< Gradient > *> &g)
Clone and attach arbitrary functors which compute the exact gradients of the EquationSystems' solutio...
const T_sys & get_system(std::string_view name) const
This is the MeshBase class.
unsigned int variable_number(std::string_view var) const
SolverPackage default_solver_package()
This class handles the numbering of degrees of freedom on a mesh.
virtual void add_matrix(const DenseMatrix< T > &dm, const std::vector< numeric_index_type > &rows, const std::vector< numeric_index_type > &cols)=0
Add the full matrix dm to the SparseMatrix.
const T & get(std::string_view) const
virtual void write_equation_systems(const std::string &fname, const EquationSystems &es, const std::set< std::string > *system_names=nullptr) override
Writes out the solution for no specific time or timestep.
void print_info(std::ostream &os=libMesh::out, const unsigned int verbosity=0, const bool global=true) const
Prints relevant information about the mesh.
void compute_error(std::string_view sys_name, std::string_view unknown_name)
Computes and stores the error in the solution value e = u-u_h, the gradient grad(e) = grad(u) - grad(...
void init(triangulateio &t)
Initializes the fields of t to nullptr/0 as necessary.
static std::unique_ptr< FEGenericBase > build(const unsigned int dim, const FEType &type)
Builds a specific finite element type.
int main(int argc, char **argv)
Real l2_error(std::string_view sys_name, std::string_view unknown_name)
DIE A HORRIBLE DEATH HERE typedef LIBMESH_DEFAULT_SCALAR_TYPE Real
T & set(const std::string &)
Real forcing(Real x, Real y)
const MeshBase & get_mesh() const
void resize(const unsigned int new_m, const unsigned int new_n)
Resizes the matrix to the specified size and calls zero().
This class implements specific orders of Gauss quadrature.
unsigned int mesh_dimension() const
Parameters parameters
Data structure holding arbitrary parameters.
virtual void init()
Initialize all the systems.
virtual System & add_system(std::string_view system_type, std::string_view name)
Add the system of type system_type named name to the systems array.
The Mesh class is a thin wrapper, around the ReplicatedMesh class by default.
const DofMap & get_dof_map() const
const SparseMatrix< Number > & get_system_matrix() const
Real scalar(Real x, Real y)
Real error_norm(std::string_view sys_name, std::string_view unknown_name, const FEMNormType &norm)