53 #include "libmesh/libmesh.h" 54 #include "libmesh/mesh.h" 55 #include "libmesh/mesh_generation.h" 56 #include "libmesh/exodusII_io.h" 57 #include "libmesh/condensed_eigen_system.h" 58 #include "libmesh/equation_systems.h" 59 #include "libmesh/fe.h" 60 #include "libmesh/quadrature_gauss.h" 61 #include "libmesh/dense_matrix.h" 62 #include "libmesh/sparse_matrix.h" 63 #include "libmesh/numeric_vector.h" 64 #include "libmesh/dof_map.h" 65 #include "libmesh/fe_interface.h" 66 #include "libmesh/getpot.h" 67 #include "libmesh/elem.h" 68 #include "libmesh/zero_function.h" 69 #include "libmesh/dirichlet_boundaries.h" 70 #include "libmesh/slepc_macro.h" 71 #include "libmesh/enum_eigen_solver_type.h" 73 #define BOUNDARY_ID 100 82 const std::string & system_name);
86 const std::string & system_name,
87 std::set<unsigned int> & global_dirichlet_dofs_set);
90 int main (
int argc,
char ** argv)
96 #ifndef LIBMESH_HAVE_EXODUS_API 97 libmesh_example_requires(
false,
"--enable-exodus");
101 #ifndef LIBMESH_HAVE_SLEPC 102 if (
init.comm().rank() == 0)
103 libMesh::err <<
"ERROR: This example requires libMesh to be\n" 104 <<
"compiled with SLEPc eigen solvers support!" 110 #ifdef LIBMESH_DEFAULT_SINGLE_PRECISION 112 libmesh_example_requires(
false,
"--disable-singleprecision");
115 #if defined(LIBMESH_USE_COMPLEX_NUMBERS) && SLEPC_VERSION_LESS_THAN(3,6,2) 118 libmesh_example_requires(
false,
"--disable-complex or use SLEPc>=3.6.2");
122 #ifndef LIBMESH_ENABLE_DIRICHLET 123 libmesh_example_requires(
false,
"--enable-dirichlet");
130 for (
int i=1; i<argc; i++)
137 libmesh_example_requires(2 <= LIBMESH_DIM,
"2D support");
140 GetPot command_line (argc, argv);
143 const std::string mesh_name =
148 const unsigned int plotting_index =
152 const unsigned int n_evals =
156 std::ostringstream mesh_name_exodus;
157 mesh_name_exodus << mesh_name <<
"_mesh.e";
168 for (
const auto & elem :
mesh.element_ptr_range())
169 for (
auto side : elem->side_index_range())
170 if (elem->neighbor_ptr (side) ==
nullptr)
195 equation_systems.
parameters.
set<
unsigned int>(
"eigenpairs") = n_evals;
196 equation_systems.
parameters.
set<
unsigned int>(
"basis vectors") = n_evals*3;
201 (
"linear solver maximum iterations") = 1000;
213 #ifdef LIBMESH_ENABLE_DIRICHLET 224 equation_systems.
init();
232 eigen_system.
solve();
242 if (plotting_index > n_evals)
244 libMesh::out <<
"WARNING: Solver did not converge for the requested eigenvector!" << std::endl;
248 std::ostringstream eigenvalue_output_name;
249 eigenvalue_output_name << mesh_name <<
"_evals.txt";
250 std::ofstream evals_file(eigenvalue_output_name.str().c_str());
252 for (
unsigned int i=0; i<nconv; i++)
257 libmesh_assert_less (eval.second,
TOLERANCE);
258 evals_file << eval.first << std::endl;
261 if (i == plotting_index)
263 #ifdef LIBMESH_HAVE_EXODUS_API 265 std::ostringstream eigenvector_output_name;
266 eigenvector_output_name << mesh_name <<
"_evec.e";
268 #endif // #ifdef LIBMESH_HAVE_EXODUS_API 274 #endif // LIBMESH_HAVE_SLEPC 283 const std::string & libmesh_dbg_var(system_name))
288 libmesh_assert_equal_to (system_name,
"Eigensystem");
290 #ifdef LIBMESH_HAVE_SLEPC 317 QGauss qrule (
dim, fe_type.default_quadrature_order());
320 fe->attach_quadrature_rule (&qrule);
323 const std::vector<Real> & JxW = fe->get_JxW();
326 const std::vector<std::vector<Real>> & phi = fe->get_phi();
330 const std::vector<std::vector<RealGradient>> & dphi = fe->get_dphi();
344 std::vector<dof_id_type> dof_indices;
353 for (
const auto & elem :
mesh.active_local_element_ptr_range())
373 const unsigned int n_dofs =
374 cast_int<unsigned int>(dof_indices.size());
375 Ke.
resize (n_dofs, n_dofs);
376 Me.
resize (n_dofs, n_dofs);
384 for (
unsigned int qp=0; qp<qrule.n_points(); qp++)
385 for (
unsigned int i=0; i<n_dofs; i++)
386 for (
unsigned int j=0; j<n_dofs; j++)
388 Me(i,j) += JxW[qp]*phi[i][qp]*phi[j][qp];
389 Ke(i,j) += JxW[qp]*(dphi[i][qp]*dphi[j][qp]);
413 #endif // LIBMESH_HAVE_SLEPC class FEType hides (possibly multiple) FEFamily and approximation orders, thereby enabling specialize...
T command_line_next(std::string name, T default_value)
Use GetPot's search()/next() functions to get following arguments from the command line...
void get_dirichlet_dofs(EquationSystems &es, const std::string &system_name, std::set< unsigned int > &global_dirichlet_dofs_set)
This is the EquationSystems class.
virtual void read(const std::string &name, void *mesh_data=nullptr, bool skip_renumber_nodes_and_elements=false, bool skip_find_neighbors=false)=0
Interfaces for reading/writing a mesh to/from a file.
ConstFunction that simply returns 0.
const SparseMatrix< Number > & get_matrix_A() const
void dof_indices(const Elem *const elem, std::vector< dof_id_type > &di) const
static constexpr Real TOLERANCE
The ExodusII_IO class implements reading meshes in the ExodusII file format from Sandia National Labs...
const SparseMatrix< Number > & get_matrix_B() const
const FEType & variable_type(const unsigned int c) const
void print_info(std::ostream &os=libMesh::out) const
Prints information about the equation systems, by default to libMesh::out.
This class allows one to associate Dirichlet boundary values with a given set of mesh boundary ids an...
The LibMeshInit class, when constructed, initializes the dependent libraries (e.g.
The libMesh namespace provides an interface to certain functionality in the library.
const EigenSolver< Number > & get_eigen_solver() const
const BoundaryInfo & get_boundary_info() const
The information about boundary ids on the mesh.
const T_sys & get_system(std::string_view name) const
virtual void solve() override
Override to solve the condensed eigenproblem with the dofs in local_non_condensed_dofs_vector strippe...
This is the MeshBase class.
This class handles the numbering of degrees of freedom on a mesh.
void libmesh_ignore(const Args &...)
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.
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 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.
unsigned int add_variable(std::string_view var, const FEType &type, const std::set< subdomain_id_type > *const active_subdomains=nullptr)
Adds the variable var to the list of variables for this system.
void initialize_condensed_dofs(const std::set< dof_id_type > &global_condensed_dofs_set=std::set< dof_id_type >())
Loop over the dofs on each processor to initialize the list of non-condensed dofs.
void attach_assemble_function(void fptr(EquationSystems &es, const std::string &name))
Register a user function to use in assembling the system matrix and RHS.
This class extends EigenSystem to allow a simple way of solving (standard or generalized) eigenvalue ...
int main(int argc, char **argv)
void assemble_matrices(EquationSystems &es, const std::string &system_name)
DIE A HORRIBLE DEATH HERE typedef LIBMESH_DEFAULT_SCALAR_TYPE Real
T & set(const std::string &)
void add_side(const dof_id_type elem, const unsigned short int side, const boundary_id_type id)
Add side side of element number elem with boundary id id to the boundary information data structure...
virtual std::pair< Real, Real > get_eigenpair(dof_id_type i) override
Override get_eigenpair() to retrieve the eigenpair for the condensed eigensolve.
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.
void set_eigenproblem_type(EigenProblemType ept)
Sets the type of the current eigen problem.
void add_dirichlet_boundary(const DirichletBoundary &dirichlet_boundary)
Adds a copy of the specified Dirichlet boundary to the system.
unsigned int get_n_converged() const
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.
Manages consistently variables, degrees of freedom, and coefficient vectors for eigenvalue problems...
The Mesh class is a thin wrapper, around the ReplicatedMesh class by default.
const DofMap & get_dof_map() const
void constrain_element_matrix(DenseMatrix< Number > &matrix, std::vector< dof_id_type > &elem_dofs, bool asymmetric_constraint_rows=true) const
Constrains the element matrix.