Brian Silverman | 72890c2 | 2015-09-19 14:37:37 -0400 | [diff] [blame] | 1 | // This file is part of Eigen, a lightweight C++ template library |
| 2 | // for linear algebra. |
| 3 | // |
| 4 | // Copyright (C) 2008-2009 Gael Guennebaud <gael.guennebaud@inria.fr> |
| 5 | |
| 6 | /* NOTE The class IterationController has been adapted from the iteration |
| 7 | * class of the GMM++ and ITL libraries. |
| 8 | */ |
| 9 | |
| 10 | //======================================================================= |
| 11 | // Copyright (C) 1997-2001 |
| 12 | // Authors: Andrew Lumsdaine <lums@osl.iu.edu> |
| 13 | // Lie-Quan Lee <llee@osl.iu.edu> |
| 14 | // |
| 15 | // This file is part of the Iterative Template Library |
| 16 | // |
| 17 | // You should have received a copy of the License Agreement for the |
| 18 | // Iterative Template Library along with the software; see the |
| 19 | // file LICENSE. |
| 20 | // |
| 21 | // Permission to modify the code and to distribute modified code is |
| 22 | // granted, provided the text of this NOTICE is retained, a notice that |
| 23 | // the code was modified is included with the above COPYRIGHT NOTICE and |
| 24 | // with the COPYRIGHT NOTICE in the LICENSE file, and that the LICENSE |
| 25 | // file is distributed with the modified code. |
| 26 | // |
| 27 | // LICENSOR MAKES NO REPRESENTATIONS OR WARRANTIES, EXPRESS OR IMPLIED. |
| 28 | // By way of example, but not limitation, Licensor MAKES NO |
| 29 | // REPRESENTATIONS OR WARRANTIES OF MERCHANTABILITY OR FITNESS FOR ANY |
| 30 | // PARTICULAR PURPOSE OR THAT THE USE OF THE LICENSED SOFTWARE COMPONENTS |
| 31 | // OR DOCUMENTATION WILL NOT INFRINGE ANY PATENTS, COPYRIGHTS, TRADEMARKS |
| 32 | // OR OTHER RIGHTS. |
| 33 | //======================================================================= |
| 34 | |
| 35 | //======================================================================== |
| 36 | // |
| 37 | // Copyright (C) 2002-2007 Yves Renard |
| 38 | // |
| 39 | // This file is a part of GETFEM++ |
| 40 | // |
| 41 | // Getfem++ is free software; you can redistribute it and/or modify |
| 42 | // it under the terms of the GNU Lesser General Public License as |
| 43 | // published by the Free Software Foundation; version 2.1 of the License. |
| 44 | // |
| 45 | // This program is distributed in the hope that it will be useful, |
| 46 | // but WITHOUT ANY WARRANTY; without even the implied warranty of |
| 47 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| 48 | // GNU Lesser General Public License for more details. |
| 49 | // You should have received a copy of the GNU Lesser General Public |
| 50 | // License along with this program; if not, write to the Free Software |
| 51 | // Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, |
| 52 | // USA. |
| 53 | // |
| 54 | //======================================================================== |
| 55 | |
| 56 | #include "../../../../Eigen/src/Core/util/NonMPL2.h" |
| 57 | |
| 58 | #ifndef EIGEN_ITERATION_CONTROLLER_H |
| 59 | #define EIGEN_ITERATION_CONTROLLER_H |
| 60 | |
| 61 | namespace Eigen { |
| 62 | |
Austin Schuh | c55b017 | 2022-02-20 17:52:35 -0800 | [diff] [blame^] | 63 | /** \ingroup IterativeLinearSolvers_Module |
Brian Silverman | 72890c2 | 2015-09-19 14:37:37 -0400 | [diff] [blame] | 64 | * \class IterationController |
| 65 | * |
| 66 | * \brief Controls the iterations of the iterative solvers |
| 67 | * |
| 68 | * This class has been adapted from the iteration class of GMM++ and ITL libraries. |
| 69 | * |
| 70 | */ |
| 71 | class IterationController |
| 72 | { |
| 73 | protected : |
| 74 | double m_rhsn; ///< Right hand side norm |
| 75 | size_t m_maxiter; ///< Max. number of iterations |
| 76 | int m_noise; ///< if noise > 0 iterations are printed |
| 77 | double m_resmax; ///< maximum residual |
| 78 | double m_resminreach, m_resadd; |
| 79 | size_t m_nit; ///< iteration number |
| 80 | double m_res; ///< last computed residual |
| 81 | bool m_written; |
| 82 | void (*m_callback)(const IterationController&); |
| 83 | public : |
| 84 | |
| 85 | void init() |
| 86 | { |
| 87 | m_nit = 0; m_res = 0.0; m_written = false; |
| 88 | m_resminreach = 1E50; m_resadd = 0.0; |
| 89 | m_callback = 0; |
| 90 | } |
| 91 | |
| 92 | IterationController(double r = 1.0E-8, int noi = 0, size_t mit = size_t(-1)) |
| 93 | : m_rhsn(1.0), m_maxiter(mit), m_noise(noi), m_resmax(r) { init(); } |
| 94 | |
| 95 | void operator ++(int) { m_nit++; m_written = false; m_resadd += m_res; } |
| 96 | void operator ++() { (*this)++; } |
| 97 | |
| 98 | bool first() { return m_nit == 0; } |
| 99 | |
| 100 | /* get/set the "noisyness" (verbosity) of the solvers */ |
| 101 | int noiseLevel() const { return m_noise; } |
| 102 | void setNoiseLevel(int n) { m_noise = n; } |
| 103 | void reduceNoiseLevel() { if (m_noise > 0) m_noise--; } |
| 104 | |
| 105 | double maxResidual() const { return m_resmax; } |
| 106 | void setMaxResidual(double r) { m_resmax = r; } |
| 107 | |
| 108 | double residual() const { return m_res; } |
| 109 | |
| 110 | /* change the user-definable callback, called after each iteration */ |
| 111 | void setCallback(void (*t)(const IterationController&)) |
| 112 | { |
| 113 | m_callback = t; |
| 114 | } |
| 115 | |
| 116 | size_t iteration() const { return m_nit; } |
| 117 | void setIteration(size_t i) { m_nit = i; } |
| 118 | |
| 119 | size_t maxIterarions() const { return m_maxiter; } |
| 120 | void setMaxIterations(size_t i) { m_maxiter = i; } |
| 121 | |
| 122 | double rhsNorm() const { return m_rhsn; } |
| 123 | void setRhsNorm(double r) { m_rhsn = r; } |
| 124 | |
| 125 | bool converged() const { return m_res <= m_rhsn * m_resmax; } |
| 126 | bool converged(double nr) |
| 127 | { |
| 128 | using std::abs; |
| 129 | m_res = abs(nr); |
| 130 | m_resminreach = (std::min)(m_resminreach, m_res); |
| 131 | return converged(); |
| 132 | } |
| 133 | template<typename VectorType> bool converged(const VectorType &v) |
| 134 | { return converged(v.squaredNorm()); } |
| 135 | |
| 136 | bool finished(double nr) |
| 137 | { |
| 138 | if (m_callback) m_callback(*this); |
| 139 | if (m_noise > 0 && !m_written) |
| 140 | { |
| 141 | converged(nr); |
| 142 | m_written = true; |
| 143 | } |
| 144 | return (m_nit >= m_maxiter || converged(nr)); |
| 145 | } |
| 146 | template <typename VectorType> |
| 147 | bool finished(const MatrixBase<VectorType> &v) |
| 148 | { return finished(double(v.squaredNorm())); } |
| 149 | |
| 150 | }; |
| 151 | |
| 152 | } // end namespace Eigen |
| 153 | |
| 154 | #endif // EIGEN_ITERATION_CONTROLLER_H |