dune-composites (2.5.1)

liptonbabuskabasis.hh
1
2#ifndef DUNE_GENEO_LIPTONBABUSKA_HH
3#define DUNE_GENEO_LIPTONBABUSKA_HH
4
5#include "subdomainbasis.hh"
6#include "arpackpp_fork.hh"
7
8namespace Dune{
9 namespace Geneo{
10
11template<class GFS, class M, class X, class Y, int dim>
12class LBBasis : public SubdomainBasis<X>
13{
14 typedef Dune::PDELab::Backend::Native<M> ISTLM;
15 typedef Dune::PDELab::Backend::Native<X> ISTLX;
16
17public:
18 LBBasis(const GFS& gfs, const M& AF_neumann, const M& AF_ovlp, const double eigenvalue_threshold, X& part_unity, int& nev, int nev_arpack, double shift) {
19 using Dune::PDELab::Backend::native;
20
21 auto AF_interior = AF_neumann;
22 native(AF_interior) -= native(AF_ovlp);
23
24 ArpackFork::ArPackPlusPlus_Algorithms<ISTLM, ISTLX> arpack(native(AF_neumann));
25 double eps = .0001;
26
27 //if (nev_arpack < nev)
28 // DUNE_THROW(Dune::ISTLError,"eigenvectors_compute is less then eigenvectors or not specified!");
29
30 std::vector<double> eigenvalues;
31 std::vector<ISTLX> eigenvectors;
32 eigenvectors.resize(nev_arpack);
33 for (int i = 0; i < nev_arpack; i++) {
34 eigenvectors[i] = native(X(gfs,0.0));
35 }
36
37 arpack.computeGenNonSymMinMagnitude(native(AF_interior), eps, nev_arpack, eigenvectors, eigenvalues, shift);
38
39
40 /*for(int i = 0; i < nev_arpack; i++){
41 auto check = eigenvectors[i];
42 native(AF_neumann).mv(eigenvectors[i],check);
43 auto check2 = eigenvectors[i];
44 native(ovlp_mat).mv(eigenvectors[i],check2);
45 check2 *= eigenvalues[i];
46 check -= check2;
47 if(native(check).infinity_norm() > 1e-6) std::cout << "Rank " << gfs.gridView().comm().rank() << " Error in EV calculation " << native(check).infinity_norm() << std::endl;
48 }*/
49
50
51 // Count eigenvectors below threshold
52 int cnt = -1;
53 if (configuration.get<bool>("threshold_eigenvectors",false)) {
54 for (int i = 0; i < nev; i++) {
55 if (eigenvalues[i] > eigenvalue_threshold) {
56 cnt = i;
57 break;
58 }
59 }
60 if (configuration.get<bool>("verbose",false))
61 std::cout << "Process " << gfs.gridView().comm().rank() << " picked " << cnt << " eigenvectors" << std::endl;
62 if (cnt == -1)
63 DUNE_THROW(Dune::ISTLError,"No eigenvalue above threshold - not enough eigenvalue solves!");
64 } else {
65 cnt = nev;
66 }
67
68 this->local_basis.resize(cnt);
69
70 for (int base_id = 0; base_id < cnt; base_id++) {
71 this->local_basis[base_id] = std::make_shared<X>(part_unity);
72 for (int it = 0; it < native(eigenvectors[base_id]).N(); it++) {
73 for(int j = 0; j < dim; j++)
74 native(*this->local_basis[base_id])[it][j] *= eigenvectors[base_id][it][j];
75 }
76 }
77
78 if (configuration.get<bool>("AddPartUnityToEigenvectors",false) && eigenvalues[0] > 1E-10) {
79 auto part_unity_basis = std::make_shared<X>(gfs,0.0);
80 *part_unity_basis = part_unity;
81 this->local_basis.insert (this->local_basis.begin(), part_unity_basis);
82 this->local_basis.pop_back();
83 }
84 }
85
86};
87
88}
89}
90
91#endif //DUNE_GENEO_GENEOBASIS_HH
Creative Commons License   |  Legal Statements / Impressum  |  Hosted by TU Dresden & Uni Heidelberg  |  generated with Hugo v0.111.3 (Sep 5, 22:35, 2025)