MFEM  v3.2
Finite element discretization library
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Pages
solvers.hpp
Go to the documentation of this file.
1 // Copyright (c) 2010, Lawrence Livermore National Security, LLC. Produced at
2 // the Lawrence Livermore National Laboratory. LLNL-CODE-443211. All Rights
3 // reserved. See file COPYRIGHT for details.
4 //
5 // This file is part of the MFEM library. For more information and source code
6 // availability see http://mfem.org.
7 //
8 // MFEM is free software; you can redistribute it and/or modify it under the
9 // terms of the GNU Lesser General Public License (as published by the Free
10 // Software Foundation) version 2.1 dated February 1999.
11 
12 #ifndef MFEM_SOLVERS
13 #define MFEM_SOLVERS
14 
15 #include "../config/config.hpp"
16 #include "operator.hpp"
17 
18 #ifdef MFEM_USE_MPI
19 #include <mpi.h>
20 #endif
21 
22 #ifdef MFEM_USE_SUITESPARSE
23 #include <umfpack.h>
24 #include <klu.h>
25 #endif
26 
27 namespace mfem
28 {
29 
31 class IterativeSolver : public Solver
32 {
33 #ifdef MFEM_USE_MPI
34 private:
35  int dot_prod_type; // 0 - local, 1 - global over 'comm'
36  MPI_Comm comm;
37 #endif
38 
39 protected:
40  const Operator *oper;
42 
44  double rel_tol, abs_tol;
45 
46  // stats
47  mutable int final_iter, converged;
48  mutable double final_norm;
49 
50  double Dot(const Vector &x, const Vector &y) const;
51  double Norm(const Vector &x) const { return sqrt(Dot(x, x)); }
52 
53 public:
55 
56 #ifdef MFEM_USE_MPI
57  IterativeSolver(MPI_Comm _comm);
58 #endif
59 
60  void SetRelTol(double rtol) { rel_tol = rtol; }
61  void SetAbsTol(double atol) { abs_tol = atol; }
62  void SetMaxIter(int max_it) { max_iter = max_it; }
63  void SetPrintLevel(int print_lvl);
64 
65  int GetNumIterations() const { return final_iter; }
66  int GetConverged() const { return converged; }
67  double GetFinalNorm() const { return final_norm; }
68 
70  virtual void SetPreconditioner(Solver &pr);
71 
73  virtual void SetOperator(const Operator &op);
74 };
75 
76 
78 class SLISolver : public IterativeSolver
79 {
80 protected:
81  mutable Vector r, z;
82 
83  void UpdateVectors();
84 
85 public:
86  SLISolver() { }
87 
88 #ifdef MFEM_USE_MPI
89  SLISolver(MPI_Comm _comm) : IterativeSolver(_comm) { }
90 #endif
91 
92  virtual void SetOperator(const Operator &op)
94 
95  virtual void Mult(const Vector &x, Vector &y) const;
96 };
97 
99 void SLI(const Operator &A, const Vector &b, Vector &x,
100  int print_iter = 0, int max_num_iter = 1000,
101  double RTOLERANCE = 1e-12, double ATOLERANCE = 1e-24);
102 
104 void SLI(const Operator &A, Solver &B, const Vector &b, Vector &x,
105  int print_iter = 0, int max_num_iter = 1000,
106  double RTOLERANCE = 1e-12, double ATOLERANCE = 1e-24);
107 
108 
110 class CGSolver : public IterativeSolver
111 {
112 protected:
113  mutable Vector r, d, z;
114 
115  void UpdateVectors();
116 
117 public:
118  CGSolver() { }
119 
120 #ifdef MFEM_USE_MPI
121  CGSolver(MPI_Comm _comm) : IterativeSolver(_comm) { }
122 #endif
123 
124  virtual void SetOperator(const Operator &op)
126 
127  virtual void Mult(const Vector &x, Vector &y) const;
128 };
129 
131 void CG(const Operator &A, const Vector &b, Vector &x,
132  int print_iter = 0, int max_num_iter = 1000,
133  double RTOLERANCE = 1e-12, double ATOLERANCE = 1e-24);
134 
136 void PCG(const Operator &A, Solver &B, const Vector &b, Vector &x,
137  int print_iter = 0, int max_num_iter = 1000,
138  double RTOLERANCE = 1e-12, double ATOLERANCE = 1e-24);
139 
140 
143 {
144 protected:
145  int m;
146 
147 public:
148  GMRESSolver() { m = 50; }
149 
150 #ifdef MFEM_USE_MPI
151  GMRESSolver(MPI_Comm _comm) : IterativeSolver(_comm) { m = 50; }
152 #endif
153 
154  void SetKDim(int dim) { m = dim; }
155 
156  virtual void Mult(const Vector &x, Vector &y) const;
157 };
158 
161 {
162 protected:
163  int m;
164 
165 public:
166  FGMRESSolver() { m = 50; }
167 
168 #ifdef MFEM_USE_MPI
169  FGMRESSolver(MPI_Comm _comm) : IterativeSolver(_comm) { m = 50; }
170 #endif
171 
172  void SetKDim(int dim) { m = dim; }
173 
174  virtual void Mult(const Vector &x, Vector &y) const;
175 };
176 
178 int GMRES(const Operator &A, Vector &x, const Vector &b, Solver &M,
179  int &max_iter, int m, double &tol, double atol, int printit);
180 
182 void GMRES(const Operator &A, Solver &B, const Vector &b, Vector &x,
183  int print_iter = 0, int max_num_iter = 1000, int m = 50,
184  double rtol = 1e-12, double atol = 1e-24);
185 
186 
189 {
190 protected:
191  mutable Vector p, phat, s, shat, t, v, r, rtilde;
192 
193  void UpdateVectors();
194 
195 public:
197 
198 #ifdef MFEM_USE_MPI
199  BiCGSTABSolver(MPI_Comm _comm) : IterativeSolver(_comm) { }
200 #endif
201 
202  virtual void SetOperator(const Operator &op)
204 
205  virtual void Mult(const Vector &x, Vector &y) const;
206 };
207 
209 int BiCGSTAB(const Operator &A, Vector &x, const Vector &b, Solver &M,
210  int &max_iter, double &tol, double atol, int printit);
211 
213 void BiCGSTAB(const Operator &A, Solver &B, const Vector &b, Vector &x,
214  int print_iter = 0, int max_num_iter = 1000,
215  double rtol = 1e-12, double atol = 1e-24);
216 
217 
220 {
221 protected:
222  mutable Vector v0, v1, w0, w1, q;
223  mutable Vector u1; // used in the preconditioned version
224 
225 public:
227 
228 #ifdef MFEM_USE_MPI
229  MINRESSolver(MPI_Comm _comm) : IterativeSolver(_comm) { }
230 #endif
231 
232  virtual void SetPreconditioner(Solver &pr)
233  {
235  if (oper) { u1.SetSize(width); }
236  }
237 
238  virtual void SetOperator(const Operator &op);
239 
240  virtual void Mult(const Vector &b, Vector &x) const;
241 };
242 
244 void MINRES(const Operator &A, const Vector &b, Vector &x, int print_it = 0,
245  int max_it = 1000, double rtol = 1e-12, double atol = 1e-24);
246 
248 void MINRES(const Operator &A, Solver &B, const Vector &b, Vector &x,
249  int print_it = 0, int max_it = 1000,
250  double rtol = 1e-12, double atol = 1e-24);
251 
252 
259 {
260 protected:
261  mutable Vector r, c;
262 
263 public:
265 
266 #ifdef MFEM_USE_MPI
267  NewtonSolver(MPI_Comm _comm) : IterativeSolver(_comm) { }
268 #endif
269  virtual void SetOperator(const Operator &op);
270 
271  void SetSolver(Solver &solver) { prec = &solver; }
272 
273  virtual void Mult(const Vector &b, Vector &x) const;
274 };
275 
276 
281 int aGMRES(const Operator &A, Vector &x, const Vector &b,
282  const Operator &M, int &max_iter,
283  int m_max, int m_min, int m_step, double cf,
284  double &tol, double &atol, int printit);
285 
286 
294 {
295 protected:
297  double a;
298 
300  inline double solve(double l, const Vector &xt, Vector &x, int &nclip) const
301  {
302  add(xt, l, w, x);
303  x.median(lo,hi);
304  nclip++;
305  return Dot(w,x)-a;
306  }
307 
308  inline void print_iteration(int it, double r, double l) const;
309 
310 public:
312 
313 #ifdef MFEM_USE_MPI
314  SLBQPOptimizer(MPI_Comm _comm) : IterativeSolver(_comm) {}
315 #endif
316 
317  void SetBounds(const Vector &_lo, const Vector &_hi);
318  void SetLinearConstraint(const Vector &_w, double _a);
319 
320  // For this problem type, we let the target values play the role of the
321  // initial vector xt, from which the operator generates the optimal vector x.
322  virtual void Mult(const Vector &xt, Vector &x) const;
323 
325  virtual void SetPreconditioner(Solver &pr);
326  virtual void SetOperator(const Operator &op);
327 };
328 
329 
330 #ifdef MFEM_USE_SUITESPARSE
331 
333 class UMFPackSolver : public Solver
334 {
335 protected:
338  void *Numeric;
339  SuiteSparse_long *AI, *AJ;
340 
341  void Init();
342 
343 public:
344  double Control[UMFPACK_CONTROL];
345  mutable double Info[UMFPACK_INFO];
346 
347  UMFPackSolver(bool _use_long_ints = false)
348  : use_long_ints(_use_long_ints) { Init(); }
349  UMFPackSolver(SparseMatrix &A, bool _use_long_ints = false)
350  : use_long_ints(_use_long_ints) { Init(); SetOperator(A); }
351 
352  // Works on sparse matrices only; calls SparseMatrix::SortColumnIndices().
353  virtual void SetOperator(const Operator &op);
354 
355  void SetPrintLevel(int print_lvl) { Control[UMFPACK_PRL] = print_lvl; }
356 
357  virtual void Mult(const Vector &b, Vector &x) const;
358  virtual void MultTranspose(const Vector &b, Vector &x) const;
359 
360  virtual ~UMFPackSolver();
361 };
362 
364 class KLUSolver : public Solver
365 {
366 protected:
368  klu_symbolic *Symbolic;
369  klu_numeric *Numeric;
370 
371  void Init();
372 
373 public:
375  : mat(0),Symbolic(0),Numeric(0)
376  { Init(); }
378  : mat(0),Symbolic(0),Numeric(0)
379  { Init(); SetOperator(A); }
380 
381  // Works on sparse matrices only; calls SparseMatrix::SortColumnIndices().
382  virtual void SetOperator(const Operator &op);
383 
384  virtual void Mult(const Vector &b, Vector &x) const;
385  virtual void MultTranspose(const Vector &b, Vector &x) const;
386 
387  virtual ~KLUSolver();
388 
389  mutable klu_common Common;
390 };
391 
392 #endif // MFEM_USE_SUITESPARSE
393 
394 }
395 
396 #endif // MFEM_SOLVERS
void SetSolver(Solver &solver)
Definition: solvers.hpp:271
Conjugate gradient method.
Definition: solvers.hpp:110
virtual void MultTranspose(const Vector &b, Vector &x) const
Action of the transpose operator.
Definition: solvers.cpp:1773
double Info[UMFPACK_INFO]
Definition: solvers.hpp:345
SparseMatrix * mat
Definition: solvers.hpp:337
int GetNumIterations() const
Definition: solvers.hpp:65
const Operator * oper
Definition: solvers.hpp:40
SuiteSparse_long * AI
Definition: solvers.hpp:339
void SetSize(int s)
Resize the vector if the new size is different.
Definition: vector.hpp:263
NewtonSolver(MPI_Comm _comm)
Definition: solvers.hpp:267
FGMRES method.
Definition: solvers.hpp:160
Direct sparse solver using KLU.
Definition: solvers.hpp:364
virtual void MultTranspose(const Vector &b, Vector &x) const
Action of the transpose operator.
Definition: solvers.cpp:1874
UMFPackSolver(SparseMatrix &A, bool _use_long_ints=false)
Definition: solvers.hpp:349
virtual void Mult(const Vector &x, Vector &y) const
Operator application.
Definition: solvers.cpp:294
MINRES method.
Definition: solvers.hpp:219
virtual void Mult(const Vector &x, Vector &y) const
Operator application.
Definition: solvers.cpp:116
void add(const Vector &v1, const Vector &v2, Vector &v)
Definition: vector.cpp:259
double Norm(const Vector &x) const
Definition: solvers.hpp:51
double GetFinalNorm() const
Definition: solvers.hpp:67
virtual void Mult(const Vector &x, Vector &y) const
Operator application.
Definition: solvers.cpp:860
int BiCGSTAB(const Operator &A, Vector &x, const Vector &b, Solver &M, int &max_iter, double &tol, double atol, int printit)
BiCGSTAB method. (tolerances are squared)
Definition: solvers.cpp:986
void SetKDim(int dim)
Definition: solvers.hpp:172
FGMRESSolver(MPI_Comm _comm)
Definition: solvers.hpp:169
Direct sparse solver using UMFPACK.
Definition: solvers.hpp:333
virtual void Mult(const Vector &x, Vector &y) const
Operator application.
Definition: solvers.cpp:521
UMFPackSolver(bool _use_long_ints=false)
Definition: solvers.hpp:347
virtual void Mult(const Vector &b, Vector &x) const
Operator application.
Definition: solvers.cpp:1023
virtual void Mult(const Vector &x, Vector &y) const
Operator application.
Definition: solvers.cpp:684
void SetLinearConstraint(const Vector &_w, double _a)
Definition: solvers.cpp:1429
int dim
Definition: ex3.cpp:47
virtual void SetPreconditioner(Solver &pr)
This should be called before SetOperator.
Definition: solvers.hpp:232
void SetPrintLevel(int print_lvl)
Definition: solvers.cpp:71
virtual void SetOperator(const Operator &op)
Also calls SetOperator for the preconditioner if there is one.
Definition: solvers.cpp:98
double solve(double l, const Vector &xt, Vector &x, int &nclip) const
Solve QP at fixed lambda.
Definition: solvers.hpp:300
Data type sparse matrix.
Definition: sparsemat.hpp:38
void MINRES(const Operator &A, const Vector &b, Vector &x, int print_it, int max_it, double rtol, double atol)
MINRES method without preconditioner. (tolerances are squared)
Definition: solvers.cpp:1171
virtual ~UMFPackSolver()
Definition: solvers.cpp:1807
void SetMaxIter(int max_it)
Definition: solvers.hpp:62
void median(const Vector &lo, const Vector &hi)
v = median(v,lo,hi) entrywise. Implementation assumes lo &lt;= hi.
Definition: vector.cpp:440
SuiteSparse_long * AJ
Definition: solvers.hpp:339
void SetKDim(int dim)
Definition: solvers.hpp:154
void CG(const Operator &A, const Vector &b, Vector &x, int print_iter, int max_num_iter, double RTOLERANCE, double ATOLERANCE)
Conjugate gradient method. (tolerances are squared)
Definition: solvers.cpp:443
void print_iteration(int it, double r, double l) const
Definition: solvers.cpp:1447
void PCG(const Operator &A, Solver &B, const Vector &b, Vector &x, int print_iter, int max_num_iter, double RTOLERANCE, double ATOLERANCE)
Preconditioned conjugate gradient method. (tolerances are squared)
Definition: solvers.cpp:456
virtual void SetOperator(const Operator &op)
Set/update the solver for the given operator.
Definition: solvers.cpp:1829
virtual void SetOperator(const Operator &op)
Also calls SetOperator for the preconditioner if there is one.
Definition: solvers.cpp:1009
double Dot(const Vector &x, const Vector &y) const
Definition: solvers.cpp:50
int GetConverged() const
Definition: solvers.hpp:66
BiCGSTABSolver(MPI_Comm _comm)
Definition: solvers.hpp:199
klu_symbolic * Symbolic
Definition: solvers.hpp:368
SLBQPOptimizer(MPI_Comm _comm)
Definition: solvers.hpp:314
virtual void Mult(const Vector &b, Vector &x) const
Operator application.
Definition: solvers.cpp:1208
CGSolver(MPI_Comm _comm)
Definition: solvers.hpp:121
void SetPrintLevel(int print_lvl)
Definition: solvers.hpp:355
Stationary linear iteration: x &lt;- x + B (b - A x)
Definition: solvers.hpp:78
void SetAbsTol(double atol)
Definition: solvers.hpp:61
void SetRelTol(double rtol)
Definition: solvers.hpp:60
double Control[UMFPACK_CONTROL]
Definition: solvers.hpp:344
Abstract base class for iterative solver.
Definition: solvers.hpp:31
virtual void Mult(const Vector &b, Vector &x) const
Operator application.
Definition: solvers.cpp:1860
virtual void SetOperator(const Operator &op)
Also calls SetOperator for the preconditioner if there is one.
Definition: solvers.cpp:1441
SLISolver(MPI_Comm _comm)
Definition: solvers.hpp:89
GMRES method.
Definition: solvers.hpp:142
GMRESSolver(MPI_Comm _comm)
Definition: solvers.hpp:151
void SetBounds(const Vector &_lo, const Vector &_hi)
Definition: solvers.cpp:1423
void UpdateVectors()
Definition: solvers.cpp:110
klu_common Common
Definition: solvers.hpp:389
virtual void SetOperator(const Operator &op)
Also calls SetOperator for the preconditioner if there is one.
Definition: solvers.hpp:202
virtual void Mult(const Vector &xt, Vector &x) const
Operator application.
Definition: solvers.cpp:1454
virtual void SetOperator(const Operator &op)
Also calls SetOperator for the preconditioner if there is one.
Definition: solvers.hpp:124
Vector data type.
Definition: vector.hpp:33
MINRESSolver(MPI_Comm _comm)
Definition: solvers.hpp:229
virtual void SetPreconditioner(Solver &pr)
This should be called before SetOperator.
Definition: solvers.cpp:92
KLUSolver(SparseMatrix &A)
Definition: solvers.hpp:377
int aGMRES(const Operator &A, Vector &x, const Vector &b, const Operator &M, int &max_iter, int m_max, int m_min, int m_step, double cf, double &tol, double &atol, int printit)
Definition: solvers.cpp:1271
virtual ~KLUSolver()
Definition: solvers.cpp:1888
void UpdateVectors()
Definition: solvers.cpp:287
BiCGSTAB method.
Definition: solvers.hpp:188
SparseMatrix * mat
Definition: solvers.hpp:367
Base class for solvers.
Definition: operator.hpp:102
virtual void SetPreconditioner(Solver &pr)
These are not currently meaningful for this solver and will error out.
Definition: solvers.cpp:1435
Abstract operator.
Definition: operator.hpp:21
klu_numeric * Numeric
Definition: solvers.hpp:369
virtual void Mult(const Vector &b, Vector &x) const
Operator application.
Definition: solvers.cpp:1741
virtual void SetOperator(const Operator &op)
Also calls SetOperator for the preconditioner if there is one.
Definition: solvers.hpp:92
void SLI(const Operator &A, const Vector &b, Vector &x, int print_iter, int max_num_iter, double RTOLERANCE, double ATOLERANCE)
Stationary linear iteration. (tolerances are squared)
Definition: solvers.cpp:259
int GMRES(const Operator &A, Vector &x, const Vector &b, Solver &M, int &max_iter, int m, double &tol, double atol, int printit)
GMRES method. (tolerances are squared)
Definition: solvers.cpp:824
virtual void SetOperator(const Operator &op)
Also calls SetOperator for the preconditioner if there is one.
Definition: solvers.cpp:1197
virtual void SetOperator(const Operator &op)
Set/update the solver for the given operator.
Definition: solvers.cpp:1641