symGaussSeidelSmoother.C
Go to the documentation of this file.
1/*---------------------------------------------------------------------------*\
2 ========= |
3 \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
4 \\ / O peration |
5 \\ / A nd | www.openfoam.com
6 \\/ M anipulation |
7-------------------------------------------------------------------------------
8 Copyright (C) 2012-2015 OpenFOAM Foundation
9 Copyright (C) 2017-2019 OpenCFD Ltd.
10-------------------------------------------------------------------------------
11License
12 This file is part of OpenFOAM.
13
14 OpenFOAM is free software: you can redistribute it and/or modify it
15 under the terms of the GNU General Public License as published by
16 the Free Software Foundation, either version 3 of the License, or
17 (at your option) any later version.
18
19 OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
20 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
21 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
22 for more details.
23
24 You should have received a copy of the GNU General Public License
25 along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
26
27\*---------------------------------------------------------------------------*/
28
30#include "PrecisionAdaptor.H"
31
32// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
33
34namespace Foam
35{
37
38 lduMatrix::smoother::addsymMatrixConstructorToTable<symGaussSeidelSmoother>
40
41 lduMatrix::smoother::addasymMatrixConstructorToTable<symGaussSeidelSmoother>
43}
44
45
46// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
47
49(
50 const word& fieldName,
51 const lduMatrix& matrix,
52 const FieldField<Field, scalar>& interfaceBouCoeffs,
53 const FieldField<Field, scalar>& interfaceIntCoeffs,
54 const lduInterfaceFieldPtrsList& interfaces
55)
56:
57 lduMatrix::smoother
58 (
59 fieldName,
60 matrix,
61 interfaceBouCoeffs,
62 interfaceIntCoeffs,
63 interfaces
64 )
65{}
66
67
68// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
69
71(
72 const word& fieldName_,
74 const lduMatrix& matrix_,
75 const solveScalarField& source,
76 const FieldField<Field, scalar>& interfaceBouCoeffs_,
77 const lduInterfaceFieldPtrsList& interfaces_,
78 const direction cmpt,
79 const label nSweeps
80)
81{
82 solveScalar* __restrict__ psiPtr = psi.begin();
83
84 const label nCells = psi.size();
85
86 solveScalarField bPrime(nCells);
87 solveScalar* __restrict__ bPrimePtr = bPrime.begin();
88
89 const scalar* const __restrict__ diagPtr = matrix_.diag().begin();
90 const scalar* const __restrict__ upperPtr =
91 matrix_.upper().begin();
92 const scalar* const __restrict__ lowerPtr =
93 matrix_.lower().begin();
94
95 const label* const __restrict__ uPtr =
96 matrix_.lduAddr().upperAddr().begin();
97
98 const label* const __restrict__ ownStartPtr =
99 matrix_.lduAddr().ownerStartAddr().begin();
100
101
102 // Parallel boundary initialisation. The parallel boundary is treated
103 // as an effective jacobi interface in the boundary.
104 // Note: there is a change of sign in the coupled
105 // interface update. The reason for this is that the
106 // internal coefficients are all located at the l.h.s. of
107 // the matrix whereas the "implicit" coefficients on the
108 // coupled boundaries are all created as if the
109 // coefficient contribution is of a source-kind (i.e. they
110 // have a sign as if they are on the r.h.s. of the matrix.
111 // To compensate for this, it is necessary to turn the
112 // sign of the contribution.
113
114 for (label sweep=0; sweep<nSweeps; sweep++)
115 {
116 bPrime = source;
117
118 const label startRequest = Pstream::nRequests();
119
121 (
122 false,
123 interfaceBouCoeffs_,
124 interfaces_,
125 psi,
126 bPrime,
127 cmpt
128 );
129
131 (
132 false,
133 interfaceBouCoeffs_,
134 interfaces_,
135 psi,
136 bPrime,
137 cmpt,
138 startRequest
139 );
140
141 solveScalar psii;
142 label fStart;
143 label fEnd = ownStartPtr[0];
144
145 for (label celli=0; celli<nCells; celli++)
146 {
147 // Start and end of this row
148 fStart = fEnd;
149 fEnd = ownStartPtr[celli + 1];
150
151 // Get the accumulated neighbour side
152 psii = bPrimePtr[celli];
153
154 // Accumulate the owner product side
155 for (label facei=fStart; facei<fEnd; facei++)
156 {
157 psii -= upperPtr[facei]*psiPtr[uPtr[facei]];
158 }
159
160 // Finish current psi
161 psii /= diagPtr[celli];
162
163 // Distribute the neighbour side using current psi
164 for (label facei=fStart; facei<fEnd; facei++)
165 {
166 bPrimePtr[uPtr[facei]] -= lowerPtr[facei]*psii;
167 }
168
169 psiPtr[celli] = psii;
170 }
171
172 fStart = ownStartPtr[nCells];
173
174 for (label celli=nCells-1; celli>=0; celli--)
175 {
176 // Start and end of this row
177 fEnd = fStart;
178 fStart = ownStartPtr[celli];
179
180 // Get the accumulated neighbour side
181 psii = bPrimePtr[celli];
182
183 // Accumulate the owner product side
184 for (label facei=fStart; facei<fEnd; facei++)
185 {
186 psii -= upperPtr[facei]*psiPtr[uPtr[facei]];
187 }
188
189 // Finish psi for this cell
190 psii /= diagPtr[celli];
191
192 // Distribute the neighbour side using psi for this cell
193 for (label facei=fStart; facei<fEnd; facei++)
194 {
195 bPrimePtr[uPtr[facei]] -= lowerPtr[facei]*psii;
196 }
197
198 psiPtr[celli] = psii;
199 }
200 }
201}
202
203
205(
207 const solveScalarField& source,
208 const direction cmpt,
209 const label nSweeps
210) const
211{
212 smooth
213 (
214 fieldName_,
215 psi,
216 matrix_,
217 source,
218 interfaceBouCoeffs_,
219 interfaces_,
220 cmpt,
221 nSweeps
222 );
223}
224
225
227(
229 const scalarField& source,
230 const direction cmpt,
231 const label nSweeps
232) const
233{
234 scalarSmooth
235 (
236 psi,
238 cmpt,
239 nSweeps
240 );
241}
242
243
244// ************************************************************************* //
A const Field/List wrapper with possible data conversion.
A field of fields is a PtrList of fields with reference counting.
Definition: FieldField.H:80
iterator begin() noexcept
Return an iterator to begin traversing the UList.
Definition: UListI.H:329
void size(const label n)
Older name for setAddressableSize.
Definition: UList.H:114
static label nRequests()
Get number of outstanding requests.
Definition: UPstream.C:90
const labelUList & ownerStartAddr() const
Return owner start addressing.
virtual const labelUList & upperAddr() const =0
Return upper addressing.
lduMatrix is a general matrix class in which the coefficients are stored as three arrays,...
Definition: lduMatrix.H:84
scalarField & upper()
Definition: lduMatrix.C:203
const lduAddressing & lduAddr() const
Return the LDU addressing.
Definition: lduMatrix.H:578
void initMatrixInterfaces(const bool add, const FieldField< Field, scalar > &interfaceCoeffs, const lduInterfaceFieldPtrsList &interfaces, const solveScalarField &psiif, solveScalarField &result, const direction cmpt) const
scalarField & lower()
Definition: lduMatrix.C:174
scalarField & diag()
Definition: lduMatrix.C:192
void updateMatrixInterfaces(const bool add, const FieldField< Field, scalar > &interfaceCoeffs, const lduInterfaceFieldPtrsList &interfaces, const solveScalarField &psiif, solveScalarField &result, const direction cmpt, const label startRequest) const
Update interfaced interfaces for matrix operations.
A lduMatrix::smoother for symmetric Gauss-Seidel.
static void smooth(const word &fieldName, solveScalarField &psi, const lduMatrix &matrix, const solveScalarField &source, const FieldField< Field, scalar > &interfaceBouCoeffs, const lduInterfaceFieldPtrsList &interfaces, const direction cmpt, const label nSweeps)
Smooth for the given number of sweeps.
virtual void scalarSmooth(solveScalarField &psi, const solveScalarField &source, const direction cmpt, const label nSweeps) const
Smooth the solution for a given number of sweeps.
A class for handling words, derived from Foam::string.
Definition: word.H:68
#define defineTypeNameAndDebug(Type, DebugSwitch)
Define the typeName and debug information.
Definition: className.H:121
const volScalarField & psi
Namespace for OpenFOAM.
lduMatrix::smoother::addasymMatrixConstructorToTable< symGaussSeidelSmoother > addsymGaussSeidelSmootherAsymMatrixConstructorToTable_
uint8_t direction
Definition: direction.H:56
lduMatrix::smoother::addsymMatrixConstructorToTable< symGaussSeidelSmoother > addsymGaussSeidelSmootherSymMatrixConstructorToTable_