leastSquaresCellCellStencil.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) 2017 OpenCFD Ltd.
9-------------------------------------------------------------------------------
10License
11 This file is part of OpenFOAM.
12
13 OpenFOAM is free software: you can redistribute it and/or modify i
14 under the terms of the GNU General Public License as published by
15 the Free Software Foundation, either version 3 of the License, or
16 (at your option) any later version.
17
18 OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
19 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
20 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
21 for more details.
22
23 You should have received a copy of the GNU General Public License
24 along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
25
26\*---------------------------------------------------------------------------*/
27
30#include "SVD.H"
31
32// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
33
34namespace Foam
35{
36namespace cellCellStencils
37{
40}
41}
42
43// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
44
46(
47 const point& sample,
48 const pointList& donorCcs,
49 scalarList& weights
50) const
51{
52 // Implicit least squares weighting
53 // Number of donors
54 label nD = donorCcs.size();
55
56 weights.setSize(nD);
57
58 // List for distance vectors and LSQ weights
59 List<vector> d(nD);
60 scalarList LSQw(nD);
61
62 // Sum of weights
63 scalar W = 0;
64
65 // Sum of weighted distance vectors
66 vector dw(Zero);
67
69
70 bool shortC = false;
71
72 // Compute distance vectors and fill rectangular matrix
73 forAll(donorCcs, j)
74 {
75 // Neighbour weights
76 d[j] = donorCcs[j] - sample;
77
78 // Check for short-circuiting if zero distance
79 // is detected with respect to any donor
80 if (mag(d[j]) < ROOTVSMALL)
81 {
82 shortC = true;
83 break;
84 }
85
86 LSQw[j] = 1.0/magSqr(d[j]);
87
88 // T matrix
89 vector wd = LSQw[j]*d[j];
90 A[j][0] = wd.x();
91 A[j][1] = wd.y();
92 A[j][2] = wd.z();
93
94 // Sum of weighted distance vectors
95 dw += wd;
96
97 // Sum of weights
98 W += LSQw[j];
99 }
100
101 if (!shortC)
102 {
103 // Use Singular Value Decomposition to avoid problems
104 // with 1D, 2D stencils
105 SVD svd(A.T()*A, SMALL);
106
107 // Least squares vectors
108 RectangularMatrix<scalar> ATAinvAT(svd.VSinvUt()*A.T());
109
110 scalar saveDiag(W);
111
112 // Diagonal coefficient
113 for (label i = 0; i < 3; i++)
114 {
115 // Get row
116 scalarList Row(UList<scalar>(ATAinvAT[i], nD));
117
118 forAll(donorCcs, j)
119 {
120 W -= Row[j]*LSQw[j]*dw[i];
121 }
122 }
123
124 if (mag(W) < SMALL*mag(saveDiag))
125 {
126 shortC = true;
127 }
128 else
129 {
130 // Compute final neighbour weights with additional scaling
131 forAll(donorCcs, j)
132 {
133 weights[j] =
134 (
135 LSQw[j]
136 - ATAinvAT[0][j]*LSQw[j]*dw[0]
137 - ATAinvAT[1][j]*LSQw[j]*dw[1]
138 - ATAinvAT[2][j]*LSQw[j]*dw[2]
139 )
140 /W;
141 }
142 }
143 }
144
145 if (shortC)
146 {
147 // Matrix ill conditioned. Use straight injection from central
148 // donor.
149 weights = 0.0;
150 weights[0] = 1.0;
151 }
152}
153
154
155// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
156
158(
159 const fvMesh& mesh,
160 const dictionary& dict,
161 const bool doUpdate
162)
163:
164 inverseDistance(mesh, dict, false)
165{
166 if (doUpdate)
167 {
168 update();
169 }
170}
171
172
173// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * //
174
176{}
177
178
179// ************************************************************************* //
static const Foam::dimensionedScalar A("", Foam::dimPressure, 611.21)
Macros for easy insertion into run-time selection tables.
#define addToRunTimeSelectionTable(baseType, thisType, argNames)
Add to construction table with typeName as the key.
Minimal example by using system/controlDict.functions:
void setSize(const label n)
Alias for resize()
Definition: List.H:218
A templated (M x N) rectangular matrix of objects of <Type>, containing M*N elements,...
Singular value decomposition of a rectangular matrix.
Definition: SVD.H:54
scalarRectangularMatrix VSinvUt() const
Return the matrix product V S^(-1) U^T (the pseudo inverse)
Definition: SVD.C:387
A 1D vector of objects of type <T>, where the size of the vector is known and can be used for subscri...
Definition: UList.H:94
void size(const label n)
Older name for setAddressableSize.
Definition: UList.H:114
const Cmpt & z() const
Access to the vector z component.
Definition: VectorI.H:85
const Cmpt & y() const
Access to the vector y component.
Definition: VectorI.H:79
const Cmpt & x() const
Access to the vector x component.
Definition: VectorI.H:73
Calculation of interpolation stencils.
Inverse-distance-weighted interpolation stencil.
virtual bool update()
Update stencils. Return false if nothing changed.
Least-squares-weighted interpolation stencil.
virtual void stencilWeights(const point &sample, const pointList &donorCcs, scalarList &weights) const
Calculate lsq weights for single acceptor.
A list of keyword definitions, which are a keyword followed by a number of values (eg,...
Definition: dictionary.H:126
dimensioned< Type > T() const
Return transpose.
Mesh data needed to do the Finite Volume discretisation.
Definition: fvMesh.H:91
#define defineTypeNameAndDebug(Type, DebugSwitch)
Define the typeName and debug information.
Definition: className.H:121
dynamicFvMesh & mesh
Namespace for OpenFOAM.
dimensioned< typename typeOfMag< Type >::type > mag(const dimensioned< Type > &dt)
static constexpr const zero Zero
Global zero (0)
Definition: zero.H:131
dimensioned< typename typeOfMag< Type >::type > magSqr(const dimensioned< Type > &dt)
dictionary dict
#define forAll(list, i)
Loop across all elements in list.
Definition: stdFoam.H:333