deal.II version GIT relicensing-2206-gaa53ff9447 2024-12-02 09:10:00+00:00
\(\newcommand{\dealvcentcolon}{\mathrel{\mathop{:}}}\) \(\newcommand{\dealcoloneq}{\dealvcentcolon\mathrel{\mkern-1.2mu}=}\) \(\newcommand{\jump}[1]{\left[\!\left[ #1 \right]\!\right]}\) \(\newcommand{\average}[1]{\left\{\!\left\{ #1 \right\}\!\right\}}\)
Loading...
Searching...
No Matches
trilinos_solver.h
Go to the documentation of this file.
1// ------------------------------------------------------------------------
2//
3// SPDX-License-Identifier: LGPL-2.1-or-later
4// Copyright (C) 2008 - 2024 by the deal.II authors
5//
6// This file is part of the deal.II library.
7//
8// Part of the source code is dual licensed under Apache-2.0 WITH
9// LLVM-exception OR LGPL-2.1-or-later. Detailed license information
10// governing the source code and code contributions can be found in
11// LICENSE.md and CONTRIBUTING.md at the top level directory of deal.II.
12//
13// ------------------------------------------------------------------------
14
15#ifndef dealii_trilinos_solver_h
16#define dealii_trilinos_solver_h
17
18
19#include <deal.II/base/config.h>
20
21#ifdef DEAL_II_WITH_TRILINOS
22
24
28# include <deal.II/lac/vector.h>
29
30// for AztecOO solvers
31# include <Amesos.h>
32# include <AztecOO.h>
33# include <Epetra_LinearProblem.h>
34# include <Epetra_Operator.h>
35
36// for Belos solvers
37# ifdef DEAL_II_TRILINOS_WITH_BELOS
38# include <BelosBlockCGSolMgr.hpp>
39# include <BelosBlockGmresSolMgr.hpp>
40# include <BelosEpetraAdapter.hpp>
41# include <BelosIteration.hpp>
42# include <BelosMultiVec.hpp>
43# include <BelosOperator.hpp>
44# include <BelosSolverManager.hpp>
45# endif
46
47# include <memory>
48
49
51
52namespace TrilinosWrappers
53{
54 // forward declarations
55# ifndef DOXYGEN
56 class SparseMatrix;
57 class PreconditionBase;
58# endif
59
60
80 {
81 public:
112
118 {
127 explicit AdditionalData(const bool output_solver_details = false,
128 const unsigned int gmres_restart_parameter = 30);
129
135
139 const unsigned int gmres_restart_parameter;
140 };
141
147
153 SolverControl &cn,
155
159 virtual ~SolverBase() = default;
160
166 void
167 solve(const SparseMatrix &A,
168 MPI::Vector &x,
169 const MPI::Vector &b,
170 const PreconditionBase &preconditioner);
171
179 void
180 solve(const Epetra_Operator &A,
181 MPI::Vector &x,
182 const MPI::Vector &b,
183 const PreconditionBase &preconditioner);
184
194 void
195 solve(const Epetra_Operator &A,
196 MPI::Vector &x,
197 const MPI::Vector &b,
198 const Epetra_Operator &preconditioner);
199
209 void
210 solve(const Epetra_Operator &A,
211 Epetra_MultiVector &x,
212 const Epetra_MultiVector &b,
213 const PreconditionBase &preconditioner);
214
225 void
226 solve(const Epetra_Operator &A,
227 Epetra_MultiVector &x,
228 const Epetra_MultiVector &b,
229 const Epetra_Operator &preconditioner);
230
231
232
243 void
244 solve(const SparseMatrix &A,
246 const ::Vector<double> &b,
247 const PreconditionBase &preconditioner);
248
260 void
263 const ::Vector<double> &b,
264 const PreconditionBase &preconditioner);
265
272 void
275 const ::LinearAlgebra::distributed::Vector<double> &b,
276 const PreconditionBase &preconditioner);
277
285 void
288 const ::LinearAlgebra::distributed::Vector<double> &b,
289 const PreconditionBase &preconditioner);
290
291
296 control() const;
297
302 int,
303 << "An error with error number " << arg1
304 << " occurred while calling a Trilinos function");
305
306 protected:
314
315 private:
320 template <typename Preconditioner>
321 void
322 do_solve(const Preconditioner &preconditioner);
323
327 template <typename Preconditioner>
328 void
329 set_preconditioner(AztecOO &solver, const Preconditioner &preconditioner);
330
336 std::unique_ptr<Epetra_LinearProblem> linear_problem;
337
342 std::unique_ptr<AztecOO_StatusTest> status_test;
343
348 AztecOO solver;
349
354 };
355
356
357 // provide a declaration for two explicit specializations
358 template <>
359 void
361 const PreconditionBase &preconditioner);
362
363 template <>
364 void
366 const Epetra_Operator &preconditioner);
367
368
374 class SolverCG : public SolverBase
375 {
376 public:
385 };
386
387
388
394 class SolverCGS : public SolverBase
395 {
396 public:
405 };
406
407
408
413 class SolverGMRES : public SolverBase
414 {
415 public:
425 };
426
427
428
436 {
437 public:
447 };
448
449
450
457 class SolverTFQMR : public SolverBase
458 {
459 public:
469 };
470
471
472
486 {
487 public:
493 {
497 explicit AdditionalData(const bool output_solver_details = false,
498 const std::string &solver_type = "Amesos_Klu");
499
505
524 std::string solver_type;
525 };
526
530 explicit SolverDirect(const AdditionalData &data = AdditionalData());
531
537
541 virtual ~SolverDirect() = default;
542
549 void
550 initialize(const SparseMatrix &A);
551
559 void
560 initialize(const SparseMatrix &A, const AdditionalData &data);
561
567 void
568 solve(MPI::Vector &x, const MPI::Vector &b);
569
575 void
577 const ::LinearAlgebra::distributed::Vector<double> &b);
578
584 void
585 vmult(MPI::Vector &x, const MPI::Vector &b) const;
586
592 void
594 const ::LinearAlgebra::distributed::Vector<double> &b) const;
595
602 void
603 solve(const SparseMatrix &A, MPI::Vector &x, const MPI::Vector &b);
604
612 void
613 solve(const SparseMatrix &A,
615 const ::Vector<double> &b);
616
623 void
626 const ::LinearAlgebra::distributed::Vector<double> &b);
627
632 control() const;
633
638 int,
639 << "An error with error number " << arg1
640 << " occurred while calling a Trilinos function");
641
642 private:
647 void
648 do_solve();
649
654
662
668 std::unique_ptr<Epetra_LinearProblem> linear_problem;
669
674 std::unique_ptr<Amesos_BaseSolver> solver;
675
680 };
681
682
683
684# ifdef DEAL_II_TRILINOS_WITH_BELOS
691 template <typename VectorType>
693 class SolverBelos
694 {
695 public:
700 enum SolverName
701 {
705 cg,
709 gmres,
710 } solver_name;
711
717 struct AdditionalData
718 {
722 AdditionalData(const SolverName solver_name = SolverName::cg,
723 const bool right_preconditioning = false)
724 : solver_name(solver_name)
725 , right_preconditioning(right_preconditioning)
726 {}
727
731 SolverName solver_name;
732
736 bool right_preconditioning;
737 };
738
742 SolverBelos(SolverControl &solver_control,
743 const AdditionalData &additional_data,
744 const Teuchos::RCP<Teuchos::ParameterList> &belos_parameters);
745
749 template <typename OperatorType, typename PreconditionerType>
750 void
751 solve(const OperatorType &a,
752 VectorType &x,
753 const VectorType &b,
754 const PreconditionerType &p);
755
756 private:
757 SolverControl &solver_control;
758 const AdditionalData additional_data;
759 const Teuchos::RCP<Teuchos::ParameterList> &belos_parameters;
760 };
761# endif
762
763} // namespace TrilinosWrappers
764
765
766
767# ifndef DOXYGEN
768
769# ifdef DEAL_II_TRILINOS_WITH_BELOS
770namespace TrilinosWrappers
771{
772 namespace internal
773 {
780 template <typename VectorType>
782 class MultiVecWrapper
783 : public Belos::MultiVec<typename VectorType::value_type>
784 {
785 public:
789 using value_type = typename VectorType::value_type;
790
794 static bool
795 this_type_is_missing_a_specialization()
796 {
797 return false;
798 }
799
803 MultiVecWrapper(VectorType &vector)
804 {
805 this->vectors.resize(1);
806 this->vectors[0].reset(
807 &vector,
808 [](auto *) { /*Nothing to do, since vector is owned outside.*/ });
809 }
810
814 MultiVecWrapper(const VectorType &vector)
815 {
816 this->vectors.resize(1);
817 this->vectors[0].reset(
818 &const_cast<VectorType &>(vector),
819 [](auto *) { /*Nothing to do, since vector is owned outside.*/ });
820 }
821
825 virtual ~MultiVecWrapper() = default;
826
830 virtual Belos::MultiVec<value_type> *
831 Clone(const int numvecs) const
832 {
833 auto new_multi_vec = new MultiVecWrapper<VectorType>;
834
835 new_multi_vec->vectors.resize(numvecs);
836
837 for (auto &vec : new_multi_vec->vectors)
838 {
839 vec = std::make_shared<VectorType>();
840
841 AssertThrow(this->vectors.size() > 0, ExcInternalError());
842 vec->reinit(*this->vectors[0]);
843 }
844
845 return new_multi_vec;
846 }
847
851 virtual Belos::MultiVec<value_type> *
852 CloneCopy() const
853 {
855 }
856
862 virtual Belos::MultiVec<value_type> *
863 CloneCopy(const std::vector<int> &index) const
864 {
865 auto new_multi_vec = new MultiVecWrapper<VectorType>;
866
867 new_multi_vec->vectors.resize(index.size());
868
869 for (unsigned int i = 0; i < index.size(); ++i)
870 {
871 AssertThrow(static_cast<unsigned int>(index[i]) <
872 this->vectors.size(),
874
875 new_multi_vec->vectors[i] = std::make_shared<VectorType>();
876
877 AssertIndexRange(index[i], this->vectors.size());
878 *new_multi_vec->vectors[i] = *this->vectors[index[i]];
879 }
880
881 return new_multi_vec;
882 }
883
889 virtual Belos::MultiVec<value_type> *
890 CloneViewNonConst(const std::vector<int> &index)
891 {
892 auto new_multi_vec = new MultiVecWrapper<VectorType>;
893
894 new_multi_vec->vectors.resize(index.size());
895
896 for (unsigned int i = 0; i < index.size(); ++i)
897 {
898 AssertThrow(static_cast<unsigned int>(index[i]) <
899 this->vectors.size(),
901
902 new_multi_vec->vectors[i].reset(
903 this->vectors[index[i]].get(),
904 [](
905 auto
906 *) { /*Nothing to do, since we are creating only a view.*/ });
907 }
908
909 return new_multi_vec;
910 }
911
917 virtual const Belos::MultiVec<value_type> *
918 CloneView(const std::vector<int> &index) const
919 {
920 auto new_multi_vec = new MultiVecWrapper<VectorType>;
921
922 new_multi_vec->vectors.resize(index.size());
923
924 for (unsigned int i = 0; i < index.size(); ++i)
925 {
926 AssertThrow(static_cast<unsigned int>(index[i]) <
927 this->vectors.size(),
929
930 new_multi_vec->vectors[i].reset(
931 this->vectors[index[i]].get(),
932 [](
933 auto
934 *) { /*Nothing to do, since we are creating only a view.*/ });
935 }
936
937 return new_multi_vec;
938 }
939
943 virtual ptrdiff_t
944 GetGlobalLength() const
945 {
946 AssertThrow(this->vectors.size() > 0, ExcInternalError());
947
948 for (unsigned int i = 1; i < this->vectors.size(); ++i)
949 AssertDimension(this->vectors[0]->size(), this->vectors[i]->size());
950
951 return this->vectors[0]->size();
952 }
953
957 virtual int
958 GetNumberVecs() const
959 {
960 return vectors.size();
961 }
962
966 virtual void
967 MvTimesMatAddMv(const value_type alpha,
968 const Belos::MultiVec<value_type> &A_,
969 const Teuchos::SerialDenseMatrix<int, value_type> &B,
970 const value_type beta)
971 {
972 const auto &A = try_to_get_underlying_vector(A_);
973
974 const unsigned int n_rows = B.numRows();
975 const unsigned int n_cols = B.numCols();
976
977 AssertThrow(n_rows == static_cast<unsigned int>(A.GetNumberVecs()),
979 AssertThrow(n_cols == static_cast<unsigned int>(this->GetNumberVecs()),
981
982 for (unsigned int i = 0; i < n_cols; ++i)
983 (*this->vectors[i]) *= beta;
984
985 for (unsigned int i = 0; i < n_cols; ++i)
986 for (unsigned int j = 0; j < n_rows; ++j)
987 this->vectors[i]->add(alpha * B(j, i), *A.vectors[j]);
988 }
989
993 virtual void
994 MvAddMv(const value_type alpha,
995 const Belos::MultiVec<value_type> &A_,
996 const value_type beta,
997 const Belos::MultiVec<value_type> &B_)
998 {
999 const auto &A = try_to_get_underlying_vector(A_);
1000 const auto &B = try_to_get_underlying_vector(B_);
1001
1002 AssertThrow(this->vectors.size() == A.vectors.size(),
1004 AssertThrow(this->vectors.size() == B.vectors.size(),
1006
1007 for (unsigned int i = 0; i < this->vectors.size(); ++i)
1008 {
1009 this->vectors[i]->equ(alpha, *A.vectors[i]);
1010 this->vectors[i]->add(beta, *B.vectors[i]);
1011 }
1012 }
1013
1017 virtual void
1018 MvScale(const value_type alpha)
1019 {
1020 for (unsigned int i = 0; i < this->vectors.size(); ++i)
1021 (*this->vectors[i]) *= alpha;
1022 }
1023
1027 virtual void
1028 MvScale(const std::vector<value_type> &alpha)
1029 {
1031 (void)alpha;
1032 }
1033
1038 virtual void
1039 MvTransMv(const value_type alpha,
1040 const Belos::MultiVec<value_type> &A_,
1041 Teuchos::SerialDenseMatrix<int, value_type> &B) const
1042 {
1043 const auto &A = try_to_get_underlying_vector(A_);
1044
1045 const unsigned int n_rows = B.numRows();
1046 const unsigned int n_cols = B.numCols();
1047
1048 AssertThrow(n_rows == static_cast<unsigned int>(A.GetNumberVecs()),
1050 AssertThrow(n_cols == static_cast<unsigned int>(this->GetNumberVecs()),
1052
1053 for (unsigned int i = 0; i < n_rows; ++i)
1054 for (unsigned int j = 0; j < n_cols; ++j)
1055 B(i, j) = alpha * ((*A.vectors[i]) * (*this->vectors[j]));
1056 }
1057
1062 virtual void
1063 MvDot(const Belos::MultiVec<value_type> &A_,
1064 std::vector<value_type> &b) const
1065 {
1066 const auto &A = try_to_get_underlying_vector(A_);
1067
1068 AssertThrow(this->vectors.size() == A.vectors.size(),
1070 AssertThrow(this->vectors.size() == b.size(), ExcInternalError());
1071
1072 for (unsigned int i = 0; i < this->vectors.size(); ++i)
1073 b[i] = (*this->vectors[i]) * (*A.vectors[i]);
1074 }
1075
1079 virtual void
1080 MvNorm(
1081 std::vector<typename Teuchos::ScalarTraits<value_type>::magnitudeType>
1082 &normvec,
1083 Belos::NormType type = Belos::TwoNorm) const
1084 {
1085 AssertThrow(type == Belos::TwoNorm, ExcNotImplemented());
1086 AssertThrow(this->vectors.size() == normvec.size(), ExcInternalError());
1087
1088 for (unsigned int i = 0; i < this->vectors.size(); ++i)
1089 normvec[i] = this->vectors[i]->l2_norm();
1090 }
1091
1095 virtual void
1096 SetBlock(const Belos::MultiVec<value_type> &A,
1097 const std::vector<int> &index)
1098 {
1100 (void)A;
1101 (void)index;
1102 }
1103
1107 virtual void
1108 MvRandom()
1109 {
1111 }
1112
1116 virtual void
1117 MvInit(const value_type alpha)
1118 {
1120 (void)alpha;
1121 }
1122
1126 virtual void
1127 MvPrint(std::ostream &os) const
1128 {
1130 (void)os;
1131 }
1132
1136 VectorType &
1137 genericVector()
1138 {
1139 AssertThrow(GetNumberVecs() == 1, ExcNotImplemented());
1140
1141 return *vectors[0];
1142 }
1143
1147 const VectorType &
1148 genericVector() const
1149 {
1150 AssertThrow(GetNumberVecs() == 1, ExcNotImplemented());
1151
1152 return *vectors[0];
1153 }
1154
1158 static MultiVecWrapper<VectorType> &
1159 try_to_get_underlying_vector(Belos::MultiVec<value_type> &vec_in)
1160 {
1161 auto vec = dynamic_cast<MultiVecWrapper<VectorType> *>(&vec_in);
1162
1164
1165 return *vec;
1166 }
1167
1171 const static MultiVecWrapper<VectorType> &
1172 try_to_get_underlying_vector(const Belos::MultiVec<value_type> &vec_in)
1173 {
1174 auto vec = dynamic_cast<const MultiVecWrapper<VectorType> *>(&vec_in);
1175
1177
1178 return *vec;
1179 }
1180
1181
1182# ifdef HAVE_BELOS_TSQR
1183 virtual void
1184 factorExplicit(Belos::MultiVec<value_type> &,
1185 Teuchos::SerialDenseMatrix<int, value_type> &,
1186 const bool = false)
1187 {
1189 }
1190
1191 virtual int
1192 revealRank(
1193 Teuchos::SerialDenseMatrix<int, value_type> &,
1194 const typename Teuchos::ScalarTraits<value_type>::magnitudeType &)
1195 {
1197 }
1198
1199# endif
1200
1201 private:
1205 std::vector<std::shared_ptr<VectorType>> vectors;
1206
1211 MultiVecWrapper() = default;
1212 };
1213
1220 template <typename OperatorType, typename VectorType>
1222 class OperatorWrapper
1223 : public Belos::Operator<typename VectorType::value_type>
1224 {
1225 public:
1229 using value_type = typename VectorType::value_type;
1230
1234 static bool
1235 this_type_is_missing_a_specialization()
1236 {
1237 return false;
1238 }
1239
1243 OperatorWrapper(const OperatorType &op)
1244 : op(op)
1245 {}
1246
1250 virtual ~OperatorWrapper() = default;
1251
1255 virtual void
1256 Apply(const Belos::MultiVec<value_type> &x,
1257 Belos::MultiVec<value_type> &y,
1258 Belos::ETrans trans = Belos::NOTRANS) const
1259 {
1260 // TODO: check for Tvmult
1261 AssertThrow(trans == Belos::NOTRANS, ExcNotImplemented());
1262
1263 op.vmult(MultiVecWrapper<VectorType>::try_to_get_underlying_vector(y)
1264 .genericVector(),
1265 MultiVecWrapper<VectorType>::try_to_get_underlying_vector(x)
1266 .genericVector());
1267 }
1268
1272 virtual bool
1273 HasApplyTranspose() const
1274 {
1275 // TODO: check for Tvmult
1276 return false;
1277 }
1278
1279 private:
1283 const OperatorType &op;
1284 };
1285
1286 } // namespace internal
1287
1288
1289
1290 template <typename VectorType>
1292 SolverBelos<VectorType>::SolverBelos(
1293 SolverControl &solver_control,
1294 const AdditionalData &additional_data,
1295 const Teuchos::RCP<Teuchos::ParameterList> &belos_parameters)
1296 : solver_control(solver_control)
1297 , additional_data(additional_data)
1298 , belos_parameters(belos_parameters)
1299 {}
1300
1301
1302
1303 template <typename VectorType>
1305 template <typename OperatorType, typename PreconditionerType>
1306 void SolverBelos<VectorType>::solve(const OperatorType &A_dealii,
1307 VectorType &x_dealii,
1308 const VectorType &b_dealii,
1309 const PreconditionerType &P_dealii)
1310 {
1311 using value_type = typename VectorType::value_type;
1312
1313 using MV = Belos::MultiVec<value_type>;
1314 using OP = Belos::Operator<value_type>;
1315
1316 Teuchos::RCP<OP> A = Teuchos::rcp(
1317 new internal::OperatorWrapper<OperatorType, VectorType>(A_dealii));
1318 Teuchos::RCP<OP> P = Teuchos::rcp(
1319 new internal::OperatorWrapper<PreconditionerType, VectorType>(P_dealii));
1320 Teuchos::RCP<MV> X =
1321 Teuchos::rcp(new internal::MultiVecWrapper<VectorType>(x_dealii));
1322 Teuchos::RCP<MV> B =
1323 Teuchos::rcp(new internal::MultiVecWrapper<VectorType>(b_dealii));
1324
1325 Teuchos::RCP<Belos::LinearProblem<value_type, MV, OP>> problem =
1326 Teuchos::rcp(new Belos::LinearProblem<value_type, MV, OP>(A, X, B));
1327
1328 if (additional_data.right_preconditioning == false)
1329 problem->setLeftPrec(P);
1330 else
1331 problem->setRightPrec(P);
1332
1333 const bool problem_set = problem->setProblem();
1334 AssertThrow(problem_set, ExcInternalError());
1335
1336 // compute initial residal
1337 VectorType r;
1338 r.reinit(x_dealii, true);
1339 A_dealii.vmult(r, x_dealii);
1340 r.sadd(-1., 1., b_dealii);
1341 const auto norm_0 = r.l2_norm();
1342
1343 if (solver_control.check(0, norm_0) != SolverControl::iterate)
1344 return;
1345
1346 double relative_tolerance_to_be_achieved =
1347 solver_control.tolerance() / norm_0;
1348 const unsigned int max_steps = solver_control.max_steps();
1349
1350 if (const auto *reduction_control =
1351 dynamic_cast<ReductionControl *>(&solver_control))
1352 relative_tolerance_to_be_achieved =
1353 std::max(relative_tolerance_to_be_achieved,
1354 reduction_control->reduction());
1355
1356 Teuchos::RCP<Teuchos::ParameterList> belos_parameters_copy(
1357 Teuchos::rcp(new Teuchos::ParameterList(*belos_parameters)));
1358
1359 belos_parameters_copy->set("Convergence Tolerance",
1360 relative_tolerance_to_be_achieved);
1361 belos_parameters_copy->set("Maximum Iterations",
1362 static_cast<int>(max_steps));
1363
1364 Teuchos::RCP<Belos::SolverManager<value_type, MV, OP>> solver;
1365
1366 if (additional_data.solver_name == SolverName::cg)
1367 solver = Teuchos::rcp(
1368 new Belos::BlockCGSolMgr<value_type, MV, OP>(problem,
1369 belos_parameters_copy));
1370 else if (additional_data.solver_name == SolverName::gmres)
1371 solver = Teuchos::rcp(
1372 new Belos::BlockGmresSolMgr<value_type, MV, OP>(problem,
1373 belos_parameters_copy));
1374 else
1376
1377 const auto flag = solver->solve();
1378
1379 solver_control.check(solver->getNumIters(), solver->achievedTol() * norm_0);
1380
1381 AssertThrow(flag == Belos::ReturnType::Converged ||
1382 ((dynamic_cast<IterationNumberControl *>(&solver_control) !=
1383 nullptr) &&
1384 (solver_control.last_step() == max_steps)),
1385 SolverControl::NoConvergence(solver_control.last_step(),
1386 solver_control.last_value()));
1387 }
1388
1389} // namespace TrilinosWrappers
1390# endif
1391
1392# endif
1393
1395
1396#endif // DEAL_II_WITH_TRILINOS
1397
1398#endif
@ iterate
Continue iteration.
virtual ~SolverBase()=default
SolverControl & control() const
void solve(const SparseMatrix &A, MPI::Vector &x, const MPI::Vector &b, const PreconditionBase &preconditioner)
const AdditionalData additional_data
std::unique_ptr< AztecOO_StatusTest > status_test
void set_preconditioner(AztecOO &solver, const Preconditioner &preconditioner)
void do_solve(const Preconditioner &preconditioner)
void solve(Epetra_Operator &A, ::LinearAlgebra::distributed::Vector< double > &x, const ::LinearAlgebra::distributed::Vector< double > &b, const PreconditionBase &preconditioner)
std::unique_ptr< Epetra_LinearProblem > linear_problem
enum TrilinosWrappers::SolverBase::SolverName solver_name
void solve(const SparseMatrix &A, ::LinearAlgebra::distributed::Vector< double > &x, const ::LinearAlgebra::distributed::Vector< double > &b, const PreconditionBase &preconditioner)
void solve(const SparseMatrix &A, ::LinearAlgebra::distributed::Vector< double > &x, const ::LinearAlgebra::distributed::Vector< double > &b)
virtual ~SolverDirect()=default
void initialize(const SparseMatrix &A)
void vmult(MPI::Vector &x, const MPI::Vector &b) const
std::unique_ptr< Amesos_BaseSolver > solver
void solve(MPI::Vector &x, const MPI::Vector &b)
std::unique_ptr< Epetra_LinearProblem > linear_problem
SolverControl & control() const
#define DEAL_II_NAMESPACE_OPEN
Definition config.h:498
#define DEAL_II_CXX20_REQUIRES(condition)
Definition config.h:175
#define DEAL_II_NAMESPACE_CLOSE
Definition config.h:499
static ::ExceptionBase & ExcTrilinosError(int arg1)
static ::ExceptionBase & ExcTrilinosError(int arg1)
static ::ExceptionBase & ExcNotImplemented()
#define AssertDimension(dim1, dim2)
#define AssertIndexRange(index, range)
static ::ExceptionBase & ExcInternalError()
#define DeclException1(Exception1, type1, outsequence)
Definition exceptions.h:511
#define AssertThrow(cond, exc)
#define DEAL_II_NOT_IMPLEMENTED()
std::vector< index_type > data
Definition mpi.cc:735
std::size_t size
Definition mpi.cc:734
std::vector< value_type > l2_norm(const typename ::Triangulation< dim, spacedim >::cell_iterator &parent, const value_type parent_value)
Tpetra::Vector< Number, LO, GO, NodeType< MemorySpace > > VectorType
SymmetricTensor< 2, dim, Number > b(const Tensor< 2, dim, Number > &F)
::VectorizedArray< Number, width > max(const ::VectorizedArray< Number, width > &, const ::VectorizedArray< Number, width > &)