SolverPerformance.C
Go to the documentation of this file.
1 /*---------------------------------------------------------------------------*\
2  ========= |
3  \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
4  \\ / O peration | Website: https://openfoam.org
5  \\ / A nd | Copyright (C) 2011-2022 OpenFOAM Foundation
6  \\/ M anipulation |
7 -------------------------------------------------------------------------------
8 License
9  This file is part of OpenFOAM.
10 
11  OpenFOAM is free software: you can redistribute it and/or modify it
12  under the terms of the GNU General Public License as published by
13  the Free Software Foundation, either version 3 of the License, or
14  (at your option) any later version.
15 
16  OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
17  ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
18  FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
19  for more details.
20 
21  You should have received a copy of the GNU General Public License
22  along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
23 
24 \*---------------------------------------------------------------------------*/
25 
26 #include "SolverPerformance.H"
27 #include "IOstreams.H"
28 
29 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
30 
31 template<class Type>
33 (
34  const Type& wApA
35 )
36 {
37  for(direction cmpt=0; cmpt<pTraits<Type>::nComponents; cmpt++)
38  {
39  singular_[cmpt] =
40  component(wApA, cmpt) < vsmall_;
41  }
42 
43  return singular();
44 }
45 
46 
47 template<class Type>
49 {
50  for(direction cmpt=0; cmpt<pTraits<Type>::nComponents; cmpt++)
51  {
52  if (!singular_[cmpt]) return false;
53  }
54 
55  return true;
56 }
57 
58 
59 template<class Type>
61 (
62  const Type& Tolerance,
63  const Type& RelTolerance
64 )
65 {
66  if (debug >= 2)
67  {
68  Info<< solverName_
69  << ": Iteration " << nIterations_
70  << " residual = " << finalResidual_
71  << endl;
72  }
73 
74  if
75  (
76  finalResidual_ < Tolerance
77  || (
78  RelTolerance
79  > small_*pTraits<Type>::one
80  && finalResidual_ < cmptMultiply(RelTolerance, initialResidual_)
81  )
82  )
83  {
84  converged_ = true;
85  }
86  else
87  {
88  converged_ = false;
89  }
90 
91  return converged_;
92 }
93 
94 
95 template<class Type>
97 (
98  Ostream& os
99 ) const
100 {
101  for(direction cmpt=0; cmpt<pTraits<Type>::nComponents; cmpt++)
102  {
104  {
105  os << indent << solverName_ << ": Solving for " << fieldName_;
106 
107  }
108  else
109  {
110  os << indent << solverName_ << ": Solving for "
111  << word(fieldName_ + pTraits<Type>::componentNames[cmpt]);
112  }
113 
114  if (singular_[cmpt])
115  {
116  os << ": solution singularity" << endl;
117  }
118  else
119  {
120  os << ", Initial residual = " << component(initialResidual_, cmpt)
121  << ", Final residual = " << component(finalResidual_, cmpt)
122  << ", No Iterations " << nIterations_
123  << endl;
124  }
125  }
126 }
127 
128 
129 template<class Type>
131 (
132  const Foam::label cmpt,
134 )
135 {
136  initialResidual_.replace(cmpt, sp.initialResidual());
137  finalResidual_.replace(cmpt, sp.finalResidual());
138  nIterations_.replace(cmpt, sp.nIterations());
139  singular_[cmpt] = sp.singular();
140 }
141 
142 
143 template<class Type>
146 {
148  (
149  solverName_,
150  fieldName_,
151  cmptMax(initialResidual_),
152  cmptMax(finalResidual_),
153  cmptMax(nIterations_),
154  converged_,
155  singular()
156  );
157 }
158 
159 
160 template<class Type>
162 (
163  const SolverPerformance<Type>& sp
164 ) const
165 {
166  return
167  (
168  solverName() != sp.solverName()
169  || fieldName() != sp.fieldName()
170  || initialResidual() != sp.initialResidual()
171  || finalResidual() != sp.finalResidual()
172  || nIterations() != sp.nIterations()
173  || converged() != sp.converged()
174  || singular() != sp.singular()
175  );
176 }
177 
178 
179 template<class Type>
181 (
182  const typename Foam::SolverPerformance<Type>& sp1,
183  const typename Foam::SolverPerformance<Type>& sp2
184 )
185 {
187  (
188  sp1.solverName(),
189  sp1.fieldName_,
190  max(sp1.initialResidual(), sp2.initialResidual()),
191  max(sp1.finalResidual(), sp2.finalResidual()),
192  max(sp1.nIterations(), sp2.nIterations()),
193  sp1.converged() && sp2.converged(),
194  sp1.singular() || sp2.singular()
195  );
196 }
197 
198 
199 template<class Type>
200 Foam::Istream& Foam::operator>>
201 (
202  Istream& is,
203  typename Foam::SolverPerformance<Type>& sp
204 )
205 {
206  is.readBeginList("SolverPerformance<Type>");
207  is >> sp.solverName_
208  >> sp.fieldName_
209  >> sp.initialResidual_
210  >> sp.finalResidual_
211  >> sp.nIterations_
212  >> sp.converged_
213  >> sp.singular_;
214  is.readEndList("SolverPerformance<Type>");
215 
216  return is;
217 }
218 
219 
220 template<class Type>
221 Foam::Ostream& Foam::operator<<
222 (
223  Ostream& os,
224  const typename Foam::SolverPerformance<Type>& sp
225 )
226 {
227  os << token::BEGIN_LIST
228  << sp.solverName_ << token::SPACE
229  << sp.fieldName_ << token::SPACE
230  << sp.initialResidual_ << token::SPACE
231  << sp.finalResidual_ << token::SPACE
232  << sp.nIterations_ << token::SPACE
233  << sp.converged_ << token::SPACE
234  << sp.singular_ << token::SPACE
235  << token::END_LIST;
236 
237  return os;
238 }
239 
240 
241 // ************************************************************************* //
Useful combination of include files which define Sin, Sout and Serr and the use of IO streams general...
An Istream is an abstract base class for all input systems (streams, files, token lists etc)....
Definition: Istream.H:60
char readBeginList(const char *funcName)
Definition: Istream.C:127
An Ostream is an abstract base class for all output systems (streams, files, token lists,...
Definition: Ostream.H:57
SolverPerformance is the class returned by the LduMatrix solver containing performance statistics.
void replace(const label cmpt, const SolverPerformance< typename pTraits< Type >::cmptType > &sp)
Replace component based on the minimal SolverPerformance.
void print(Ostream &os) const
Print summary of solver performance to the given stream.
const word & solverName() const
Return solver name.
const labelType & nIterations() const
Return number of iterations.
bool singular() const
Is the matrix singular?
bool checkSingularity(const Type &residual)
Singularity test.
const Type & initialResidual() const
Return initial residual.
const Type & finalResidual() const
Return final residual.
bool checkConvergence(const Type &tolerance, const Type &relTolerance)
Check, store and return convergence.
SolverPerformance< typename pTraits< Type >::cmptType > max()
Return the summary maximum of SolverPerformance<Type>
bool converged() const
Has the solver converged?
Traits class for primitives.
Definition: pTraits.H:53
A class for handling words, derived from string.
Definition: word.H:62
intWM_LABEL_SIZE_t label
A label is an int32_t or int64_t as specified by the pre-processor macro WM_LABEL_SIZE.
Definition: label.H:59
Ostream & endl(Ostream &os)
Add newline and flush stream.
Definition: Ostream.H:257
void component(FieldField< Field, typename FieldField< Field, Type >::cmptType > &sf, const FieldField< Field, Type > &f, const direction d)
messageStream Info
layerAndWeight max(const layerAndWeight &a, const layerAndWeight &b)
dimensioned< Type > cmptMultiply(const dimensioned< Type > &, const dimensioned< Type > &)
void cmptMax(FieldField< Field, typename FieldField< Field, Type >::cmptType > &cf, const FieldField< Field, Type > &f)
Ostream & indent(Ostream &os)
Indent stream.
Definition: Ostream.H:227
uint8_t direction
Definition: direction.H:45