surfaceInterpolationScheme.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) 2011-2016 OpenFOAM Foundation
9  Copyright (C) 2019-2021 OpenCFD Ltd.
10 -------------------------------------------------------------------------------
11 License
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 "volFields.H"
31 #include "surfaceFields.H"
32 #include "geometricOneField.H"
33 #include "coupledFvPatchField.H"
34 
35 // * * * * * * * * * * * * * * * * * Selectors * * * * * * * * * * * * * * * //
36 
37 template<class Type>
40 (
41  const fvMesh& mesh,
42  Istream& schemeData
43 )
44 {
45  if (schemeData.eof())
46  {
47  FatalIOErrorInFunction(schemeData)
48  << "Discretisation scheme not specified\n\n"
49  << "Valid schemes:\n"
50  << MeshConstructorTablePtr_->sortedToc()
51  << exit(FatalIOError);
52  }
53 
54  const word schemeName(schemeData);
55 
57  {
58  InfoInFunction << "Discretisation scheme = " << schemeName << endl;
59  }
60 
61  auto* ctorPtr = MeshConstructorTable(schemeName);
62 
63  if (!ctorPtr)
64  {
66  (
67  schemeData,
68  "discretisation",
69  schemeName,
70  *MeshConstructorTablePtr_
71  ) << exit(FatalIOError);
72  }
73 
74  return ctorPtr(mesh, schemeData);
75 }
76 
77 
78 template<class Type>
81 (
82  const fvMesh& mesh,
83  const surfaceScalarField& faceFlux,
84  Istream& schemeData
85 )
86 {
87  if (schemeData.eof())
88  {
89  FatalIOErrorInFunction(schemeData)
90  << "Discretisation scheme not specified"
91  << endl << endl
92  << "Valid schemes are :" << endl
93  << MeshConstructorTablePtr_->sortedToc()
94  << exit(FatalIOError);
95  }
96 
97  const word schemeName(schemeData);
98 
100  {
101  InfoInFunction << "Discretisation scheme = " << schemeName << endl;
102  }
103 
104  auto* ctorPtr = MeshFluxConstructorTable(schemeName);
105 
106  if (!ctorPtr)
107  {
109  (
110  schemeData,
111  "discretisation",
112  schemeName,
113  *MeshFluxConstructorTablePtr_
114  ) << exit(FatalIOError);
115  }
116 
117  return ctorPtr(mesh, faceFlux, schemeData);
118 }
119 
120 
121 // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
122 
123 template<class Type>
126 (
128  const tmp<surfaceScalarField>& tlambdas,
129  const tmp<surfaceScalarField>& tys
130 )
131 {
133  {
135  << "Interpolating "
136  << vf.type() << " "
137  << vf.name()
138  << " from cells to faces without explicit correction"
139  << endl;
140  }
141 
142  const surfaceScalarField& lambdas = tlambdas();
143  const surfaceScalarField& ys = tys();
144 
145  const Field<Type>& vfi = vf;
146  const scalarField& lambda = lambdas;
147  const scalarField& y = ys;
148 
149  const fvMesh& mesh = vf.mesh();
150  const labelUList& P = mesh.owner();
151  const labelUList& N = mesh.neighbour();
152 
154  (
156  (
157  IOobject
158  (
159  "interpolate("+vf.name()+')',
160  vf.instance(),
161  vf.db()
162  ),
163  mesh,
164  vf.dimensions()
165  )
166  );
168 
169  Field<Type>& sfi = sf.primitiveFieldRef();
170 
171  for (label fi=0; fi<P.size(); fi++)
172  {
173  sfi[fi] = lambda[fi]*vfi[P[fi]] + y[fi]*vfi[N[fi]];
174  }
175 
176 
177  // Interpolate across coupled patches using given lambdas and ys
179  Boundary& sfbf = sf.boundaryFieldRef();
180 
181  forAll(lambdas.boundaryField(), pi)
182  {
183  const fvsPatchScalarField& pLambda = lambdas.boundaryField()[pi];
184  const fvsPatchScalarField& pY = ys.boundaryField()[pi];
185 
186  if (vf.boundaryField()[pi].coupled())
187  {
188  sfbf[pi] =
189  pLambda*vf.boundaryField()[pi].patchInternalField()
190  + pY*vf.boundaryField()[pi].patchNeighbourField();
191  }
192  else
193  {
194  sfbf[pi] = vf.boundaryField()[pi];
195  }
196  }
197 
198  tlambdas.clear();
199  tys.clear();
200 
201  return tsf;
202 }
203 
204 
205 template<class Type>
206 template<class SFType>
207 Foam::tmp
208 <
210  <
214  >
215 >
217 (
218  const SFType& Sf,
220  const tmp<surfaceScalarField>& tlambdas
221 )
222 {
224  {
226  << "Interpolating "
227  << vf.type() << " "
228  << vf.name()
229  << " from cells to faces without explicit correction"
230  << endl;
231  }
232 
234  RetType;
235 
236  const surfaceScalarField& lambdas = tlambdas();
237 
238  const Field<Type>& vfi = vf;
239  const scalarField& lambda = lambdas;
240 
241  const fvMesh& mesh = vf.mesh();
242  const labelUList& P = mesh.owner();
243  const labelUList& N = mesh.neighbour();
244 
245  tmp<GeometricField<RetType, fvsPatchField, surfaceMesh>> tsf
246  (
247  new GeometricField<RetType, fvsPatchField, surfaceMesh>
248  (
249  IOobject
250  (
251  "interpolate("+vf.name()+')',
252  vf.instance(),
253  vf.db()
254  ),
255  mesh,
256  Sf.dimensions()*vf.dimensions()
257  )
258  );
259  GeometricField<RetType, fvsPatchField, surfaceMesh>& sf = tsf.ref();
260 
261  Field<RetType>& sfi = sf.primitiveFieldRef();
262 
263  const typename SFType::Internal& Sfi = Sf();
264 
265  for (label fi=0; fi<P.size(); fi++)
266  {
267  sfi[fi] = Sfi[fi] & (lambda[fi]*(vfi[P[fi]] - vfi[N[fi]]) + vfi[N[fi]]);
268  }
269 
270  // Interpolate across coupled patches using given lambdas
271 
272  typename GeometricField<RetType, fvsPatchField, surfaceMesh>::
273  Boundary& sfbf = sf.boundaryFieldRef();
274 
275  forAll(lambdas.boundaryField(), pi)
276  {
277  const fvsPatchScalarField& pLambda = lambdas.boundaryField()[pi];
278  const typename SFType::Patch& pSf = Sf.boundaryField()[pi];
279  fvsPatchField<RetType>& psf = sfbf[pi];
280 
281  if (vf.boundaryField()[pi].coupled())
282  {
283  psf =
284  pSf
285  & (
286  pLambda*vf.boundaryField()[pi].patchInternalField()
287  + (1.0 - pLambda)*vf.boundaryField()[pi].patchNeighbourField()
288  );
289  }
290  else
291  {
292  psf = pSf & vf.boundaryField()[pi];
293  }
294  }
295 
296  tlambdas.clear();
297 
298 // tsf.ref().oriented() = Sf.oriented();
299 
300  return tsf;
301 }
302 
303 
304 template<class Type>
307 (
309  const tmp<surfaceScalarField>& tlambdas
310 )
311 {
312  return dotInterpolate(geometricOneField(), vf, tlambdas);
313 }
314 
315 
316 template<class Type>
317 Foam::tmp
318 <
320  <
324  >
325 >
327 (
328  const surfaceVectorField& Sf,
330 ) const
331 {
333  {
335  << "Interpolating "
336  << vf.type() << " "
337  << vf.name()
338  << " from cells to faces"
339  << endl;
340  }
341 
342  tmp
343  <
344  GeometricField
345  <
347  fvsPatchField,
348  surfaceMesh
349  >
350  > tsf = dotInterpolate(Sf, vf, weights(vf));
351 
352  tsf.ref().oriented() = Sf.oriented();
353 
354  if (corrected())
355  {
356  tsf.ref() += Sf & correction(vf);
357  }
358 
359  return tsf;
360 }
361 
362 
363 template<class Type>
364 Foam::tmp
365 <
367  <
371  >
372 >
374 (
375  const surfaceVectorField& Sf,
376  const tmp<GeometricField<Type, fvPatchField, volMesh>>& tvf
377 ) const
378 {
379  tmp
380  <
381  GeometricField
382  <
384  fvsPatchField,
385  surfaceMesh
386  >
387  > tSfDotinterpVf = dotInterpolate(Sf, tvf());
388 
389  tvf.clear();
390  return tSfDotinterpVf;
391 }
392 
393 
394 template<class Type>
397 (
399 ) const
400 {
402  {
404  << "Interpolating "
405  << vf.type() << " "
406  << vf.name()
407  << " from cells to faces"
408  << endl;
409  }
410 
412  = interpolate(vf, weights(vf));
413 
414  if (corrected())
415  {
416  tsf.ref() += correction(vf);
417  }
418 
419  return tsf;
420 }
421 
422 
423 template<class Type>
426 (
428 ) const
429 {
431  = interpolate(tvf());
432  tvf.clear();
433  return tinterpVf;
434 }
435 
436 
437 // ************************************************************************* //
Foam::expressions::patchExpr::debug
int debug
Static debugging option.
volFields.H
Foam::scalarField
Field< scalar > scalarField
Specialisation of Field<T> for scalar.
Definition: primitiveFieldsFwd.H:52
Foam::IOobject
Defines the attributes of an object for which implicit objectRegistry management is supported,...
Definition: IOobject.H:169
Foam::surfaceInterpolationScheme::New
static tmp< surfaceInterpolationScheme< Type > > New(const fvMesh &mesh, Istream &schemeData)
Return new tmp interpolation scheme.
Definition: surfaceInterpolationScheme.C:40
Foam::surfaceInterpolationScheme::dotInterpolate
static tmp< GeometricField< typename innerProduct< typename SFType::value_type, Type >::type, fvsPatchField, surfaceMesh > > dotInterpolate(const SFType &Sf, const GeometricField< Type, fvPatchField, volMesh > &vf, const tmp< surfaceScalarField > &tlambdas)
Return the face-interpolate of the given cell field.
InfoInFunction
#define InfoInFunction
Report an information message using Foam::Info.
Definition: messageStream.H:350
Foam::word
A class for handling words, derived from Foam::string.
Definition: word.H:65
Foam::tmp::clear
void clear() const noexcept
Definition: tmpI.H:287
Foam::fvc::dotInterpolate
static tmp< GeometricField< typename innerProduct< vector, Type >::type, fvsPatchField, surfaceMesh > > dotInterpolate(const surfaceVectorField &Sf, const GeometricField< Type, fvPatchField, volMesh > &tvf)
Interpolate field onto faces.
Foam::tmp
A class for managing temporary objects.
Definition: PtrList.H:61
Foam::surfaceInterpolationScheme::interpolate
static tmp< GeometricField< Type, fvsPatchField, surfaceMesh > > interpolate(const GeometricField< Type, fvPatchField, volMesh > &, const tmp< surfaceScalarField > &, const tmp< surfaceScalarField > &)
Return the face-interpolate of the given cell field.
Definition: surfaceInterpolationScheme.C:126
Foam::fvsPatchScalarField
fvsPatchField< scalar > fvsPatchScalarField
Definition: fvsPatchFieldsFwd.H:45
Foam::surfaceMesh
Mesh data needed to do the Finite Volume discretisation.
Definition: surfaceMesh.H:49
Foam::fvsPatchField
An abstract base class with a fat-interface to all derived classes covering all possible ways in whic...
Definition: fvsPatchField.H:68
Foam::geometricOneField
A class representing the concept of a GeometricField of 1 used to avoid unnecessary manipulations for...
Definition: geometricOneField.H:55
Foam::FatalIOError
IOerror FatalIOError
Foam::endl
Ostream & endl(Ostream &os)
Add newline and flush stream.
Definition: Ostream.H:369
surfaceFields.H
Foam::surfaceFields.
Foam::correction
tmp< fvMatrix< Type > > correction(const fvMatrix< Type > &)
forAll
#define forAll(list, i)
Loop across all elements in list.
Definition: stdFoam.H:296
Foam::tmp::ref
T & ref() const
Definition: tmpI.H:227
FatalIOErrorInLookup
#define FatalIOErrorInLookup(ios, lookupTag, lookupName, lookupTable)
Report an error message using Foam::FatalIOError.
Definition: error.H:478
Foam::Field
Generic templated field type.
Definition: Field.H:63
Foam::Istream
An Istream is an abstract base class for all input systems (streams, files, token lists etc)....
Definition: Istream.H:61
Foam::IOstream::eof
bool eof() const noexcept
True if end of input seen.
Definition: IOstream.H:239
lambda
dimensionedScalar lambda("lambda", dimTime/sqr(dimLength), laminarTransport)
mesh
dynamicFvMesh & mesh
Definition: createDynamicFvMesh.H:6
Foam::fvMesh
Mesh data needed to do the Finite Volume discretisation.
Definition: fvMesh.H:85
Foam::exit
errorManipArg< error, int > exit(error &err, const int errNo=1)
Definition: errorManip.H:130
Foam::GeometricField::primitiveFieldRef
Internal::FieldType & primitiveFieldRef(const bool updateAccessTime=true)
Return a reference to the internal field.
Definition: GeometricField.C:766
geometricOneField.H
Foam::constant::mathematical::pi
constexpr scalar pi(M_PI)
Foam::surfaceScalarField
GeometricField< scalar, fvsPatchField, surfaceMesh > surfaceScalarField
Definition: surfaceFieldsFwd.H:54
Foam::GeometricField::ref
Internal & ref(const bool updateAccessTime=true)
Return a reference to the dimensioned internal field.
Definition: GeometricField.C:749
Foam::GeometricField::boundaryFieldRef
Boundary & boundaryFieldRef(const bool updateAccessTime=true)
Return a reference to the boundary field.
Definition: GeometricField.C:783
Foam::UList< label >
Foam::surfaceInterpolationScheme
Abstract base class for surface interpolation schemes.
Definition: surfaceInterpolationScheme.H:57
FatalIOErrorInFunction
#define FatalIOErrorInFunction(ios)
Report an error message using Foam::FatalIOError.
Definition: error.H:473
Foam::UList::size
void size(const label n)
Older name for setAddressableSize.
Definition: UList.H:114
N
const Vector< label > N(dict.get< Vector< label >>("N"))
coupledFvPatchField.H
Foam::labelUList
UList< label > labelUList
A UList of labels.
Definition: UList.H:85
Foam::surfaceVectorField
GeometricField< vector, fvsPatchField, surfaceMesh > surfaceVectorField
Definition: surfaceFieldsFwd.H:59
Foam::GeometricField< scalar, fvsPatchField, surfaceMesh >
Foam::fac::interpolate
static tmp< GeometricField< Type, faePatchField, edgeMesh > > interpolate(const GeometricField< Type, faPatchField, areaMesh > &tvf, const edgeScalarField &faceFlux, Istream &schemeData)
Interpolate field onto faces using scheme given by Istream.
surfaceInterpolationScheme.H
Foam::innerProduct::type
typeOfRank< typename pTraits< arg1 >::cmptType, direction(pTraits< arg1 >::rank)+direction(pTraits< arg2 >::rank) - 2 >::type type
Definition: products.H:149
Foam::GeometricField::boundaryField
const Boundary & boundaryField() const
Return const-reference to the boundary field.
Definition: GeometricFieldI.H:62
y
scalar y
Definition: LISASMDCalcMethod1.H:14