Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026 #include <OpenFOAM/DILUPreconditioner.H>
00027
00028
00029
00030 namespace Foam
00031 {
00032 defineTypeNameAndDebug(DILUPreconditioner, 0);
00033
00034 lduMatrix::preconditioner::
00035 addasymMatrixConstructorToTable<DILUPreconditioner>
00036 addDILUPreconditionerAsymMatrixConstructorToTable_;
00037 }
00038
00039
00040
00041
00042 Foam::DILUPreconditioner::DILUPreconditioner
00043 (
00044 const lduMatrix::solver& sol,
00045 const dictionary&
00046 )
00047 :
00048 lduMatrix::preconditioner(sol),
00049 rD_(sol.matrix().diag())
00050 {
00051 calcReciprocalD(rD_, sol.matrix());
00052 }
00053
00054
00055
00056
00057 void Foam::DILUPreconditioner::calcReciprocalD
00058 (
00059 scalarField& rD,
00060 const lduMatrix& matrix
00061 )
00062 {
00063 scalar* __restrict__ rDPtr = rD.begin();
00064
00065 const label* const __restrict__ uPtr = matrix.lduAddr().upperAddr().begin();
00066 const label* const __restrict__ lPtr = matrix.lduAddr().lowerAddr().begin();
00067
00068 const scalar* const __restrict__ upperPtr = matrix.upper().begin();
00069 const scalar* const __restrict__ lowerPtr = matrix.lower().begin();
00070
00071 register label nFaces = matrix.upper().size();
00072 for (register label face=0; face<nFaces; face++)
00073 {
00074 rDPtr[uPtr[face]] -= upperPtr[face]*lowerPtr[face]/rDPtr[lPtr[face]];
00075 }
00076
00077
00078
00079 register label nCells = rD.size();
00080
00081 for (register label cell=0; cell<nCells; cell++)
00082 {
00083 rDPtr[cell] = 1.0/rDPtr[cell];
00084 }
00085 }
00086
00087
00088 void Foam::DILUPreconditioner::precondition
00089 (
00090 scalarField& wA,
00091 const scalarField& rA,
00092 const direction
00093 ) const
00094 {
00095 scalar* __restrict__ wAPtr = wA.begin();
00096 const scalar* __restrict__ rAPtr = rA.begin();
00097 const scalar* __restrict__ rDPtr = rD_.begin();
00098
00099 const label* const __restrict__ uPtr =
00100 solver_.matrix().lduAddr().upperAddr().begin();
00101 const label* const __restrict__ lPtr =
00102 solver_.matrix().lduAddr().lowerAddr().begin();
00103 const label* const __restrict__ losortPtr =
00104 solver_.matrix().lduAddr().losortAddr().begin();
00105
00106 const scalar* const __restrict__ upperPtr =
00107 solver_.matrix().upper().begin();
00108 const scalar* const __restrict__ lowerPtr =
00109 solver_.matrix().lower().begin();
00110
00111 register label nCells = wA.size();
00112 register label nFaces = solver_.matrix().upper().size();
00113 register label nFacesM1 = nFaces - 1;
00114
00115 for (register label cell=0; cell<nCells; cell++)
00116 {
00117 wAPtr[cell] = rDPtr[cell]*rAPtr[cell];
00118 }
00119
00120
00121 register label sface;
00122
00123 for (register label face=0; face<nFaces; face++)
00124 {
00125 sface = losortPtr[face];
00126 wAPtr[uPtr[sface]] -=
00127 rDPtr[uPtr[sface]]*lowerPtr[sface]*wAPtr[lPtr[sface]];
00128 }
00129
00130 for (register label face=nFacesM1; face>=0; face--)
00131 {
00132 wAPtr[lPtr[face]] -=
00133 rDPtr[lPtr[face]]*upperPtr[face]*wAPtr[uPtr[face]];
00134 }
00135 }
00136
00137
00138 void Foam::DILUPreconditioner::preconditionT
00139 (
00140 scalarField& wT,
00141 const scalarField& rT,
00142 const direction
00143 ) const
00144 {
00145 scalar* __restrict__ wTPtr = wT.begin();
00146 const scalar* __restrict__ rTPtr = rT.begin();
00147 const scalar* __restrict__ rDPtr = rD_.begin();
00148
00149 const label* const __restrict__ uPtr =
00150 solver_.matrix().lduAddr().upperAddr().begin();
00151 const label* const __restrict__ lPtr =
00152 solver_.matrix().lduAddr().lowerAddr().begin();
00153 const label* const __restrict__ losortPtr =
00154 solver_.matrix().lduAddr().losortAddr().begin();
00155
00156 const scalar* const __restrict__ upperPtr =
00157 solver_.matrix().upper().begin();
00158 const scalar* const __restrict__ lowerPtr =
00159 solver_.matrix().lower().begin();
00160
00161 register label nCells = wT.size();
00162 register label nFaces = solver_.matrix().upper().size();
00163 register label nFacesM1 = nFaces - 1;
00164
00165 for (register label cell=0; cell<nCells; cell++)
00166 {
00167 wTPtr[cell] = rDPtr[cell]*rTPtr[cell];
00168 }
00169
00170 for (register label face=0; face<nFaces; face++)
00171 {
00172 wTPtr[uPtr[face]] -=
00173 rDPtr[uPtr[face]]*upperPtr[face]*wTPtr[lPtr[face]];
00174 }
00175
00176
00177 register label sface;
00178
00179 for (register label face=nFacesM1; face>=0; face--)
00180 {
00181 sface = losortPtr[face];
00182 wTPtr[lPtr[sface]] -=
00183 rDPtr[lPtr[sface]]*lowerPtr[sface]*wTPtr[uPtr[sface]];
00184 }
00185 }
00186
00187
00188