mirror of
https://develop.openfoam.com/Development/openfoam.git
synced 2025-11-28 03:28:01 +00:00
ENH: turbulentDFSEMInlet: refactoring by PatchFunction1
- ENH: turbulentDFSEMInlet: add normalisation factors for input Reynolds stresses, mean velocity and integral-length scales as entries `Uref` and `Lref`. - ENH: turbulentDFSEMInlet: add scaling factor entries, `scale` and `m`, to enable users to tune C1 normalisation coefficient, if need be. - BUG: turbulentDFSEM: (fixes #1004 #1744 #2089) - see #2090 for theoretical issues related to the DFSEM method.
This commit is contained in:
committed by
Andrew Heather
parent
c6759692ba
commit
b9c174312b
@ -6,7 +6,7 @@
|
||||
\\/ M anipulation |
|
||||
-------------------------------------------------------------------------------
|
||||
Copyright (C) 2015 OpenFOAM Foundation
|
||||
Copyright (C) 2016-2020 OpenCFD Ltd.
|
||||
Copyright (C) 2016-2021 OpenCFD Ltd.
|
||||
-------------------------------------------------------------------------------
|
||||
License
|
||||
This file is part of OpenFOAM.
|
||||
@ -49,37 +49,37 @@ bool Foam::eddy::setScales
|
||||
vector& alpha
|
||||
) const
|
||||
{
|
||||
// Static array of gamma^2 vs c2 coefficient
|
||||
// Static array of gamma^2 vs c2 coefficient (PCR:Table 1)
|
||||
static const scalar gamma2VsC2[8] =
|
||||
{2, 1.875, 1.737, 1.75, 0.91, 0.825, 0.806, 1.5};
|
||||
|
||||
scalar gamma = Foam::sqrt(scalar(gamma2));
|
||||
const scalar gamma = Foam::sqrt(scalar(gamma2));
|
||||
|
||||
// c2 coefficient retrieved from array
|
||||
scalar c2 = gamma2VsC2[gamma2 - 1];
|
||||
const scalar c2 = gamma2VsC2[gamma2 - 1];
|
||||
|
||||
// Length scale in largest eigenvalue direction
|
||||
label d1 = dir1_;
|
||||
label d2 = (d1 + 1) % 3;
|
||||
label d3 = (d1 + 2) % 3;
|
||||
// Length scale in the largest eigenvalue direction
|
||||
const label d1 = dir1_;
|
||||
const label d2 = (d1 + 1) % 3;
|
||||
const label d3 = (d1 + 2) % 3;
|
||||
|
||||
sigma[d1] = sigmaX;
|
||||
|
||||
// Note: sigma_average = 1/3*(sigma_x + sigma_y + sigma_z)
|
||||
// Substituting for sigma_y = sigma_x/gamma and sigma_z = sigma_y
|
||||
//sigma[d1] = 3*sigmaX/(1 + 2/gamma);
|
||||
// Other length scales equal, as function of major axis length and gamma
|
||||
sigma[d2] = sigma[d1]/gamma;
|
||||
sigma[d3] = sigma[d2];
|
||||
|
||||
vector sigma2 = cmptMultiply(sigma, sigma);
|
||||
scalar slos2 = cmptSum(cmptDivide(lambda, sigma2));
|
||||
// (PCR:Eq. 13)
|
||||
const vector sigma2(cmptMultiply(sigma, sigma));
|
||||
const scalar slos2 = cmptSum(cmptDivide(lambda, sigma2));
|
||||
|
||||
bool ok = true;
|
||||
|
||||
for (label beta = 0; beta < 3; ++beta)
|
||||
for (label beta = 0; beta < vector::nComponents; ++beta)
|
||||
{
|
||||
scalar x = slos2 - 2*lambda[beta]/sigma2[beta];
|
||||
const scalar x = slos2 - 2*lambda[beta]/sigma2[beta];
|
||||
|
||||
if (x < 0)
|
||||
{
|
||||
@ -88,6 +88,7 @@ bool Foam::eddy::setScales
|
||||
}
|
||||
else
|
||||
{
|
||||
// (SST:Eq. 23)
|
||||
alpha[beta] = e[beta]*sqrt(x/(2*c2));
|
||||
}
|
||||
}
|
||||
@ -145,7 +146,7 @@ Foam::eddy::eddy
|
||||
dir1_(0)
|
||||
{
|
||||
// Principal stresses - eigenvalues returned in ascending order
|
||||
vector lambda(eigenValues(R));
|
||||
const vector lambda(eigenValues(R));
|
||||
|
||||
// Eddy rotation from principal-to-global axes
|
||||
// - given by the 3 eigenvectors of the Reynold stress tensor as rows in
|
||||
@ -174,17 +175,17 @@ Foam::eddy::eddy
|
||||
{
|
||||
// Random length scale ratio, gamma = sigmax/sigmay = sigmax/sigmaz
|
||||
// - using gamma^2 to ease lookup of c2 coefficient
|
||||
label g2 = Gamma2[i];
|
||||
const label gamma2 = Gamma2[i];
|
||||
|
||||
if (setScales(sigmaX, g2, e, lambda, sigma_, alpha_))
|
||||
if (setScales(sigmaX, gamma2, e, lambda, sigma_, alpha_))
|
||||
{
|
||||
found = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// Normalisation coefficient (eq. 11)
|
||||
// Note: sqrt(10*V)/sqrt(nEddy) applied outside when computing uDash
|
||||
// Normalisation coefficient (PCR:Eq. 11)
|
||||
// Note: sqrt(10*V)/sqrt(nEddy) applied outside when computing uPrime
|
||||
c1_ = cmptAv(sigma_)/cmptProduct(sigma_)*cmptMin(sigma_);
|
||||
|
||||
if (found)
|
||||
@ -226,27 +227,27 @@ Foam::eddy::eddy(const eddy& e)
|
||||
|
||||
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
|
||||
|
||||
Foam::vector Foam::eddy::uDash(const point& xp, const vector& n) const
|
||||
Foam::vector Foam::eddy::uPrime(const point& xp, const vector& n) const
|
||||
{
|
||||
// Relative position inside eddy (global system)
|
||||
const vector r = cmptDivide(xp - position(n), sigma_);
|
||||
// Relative position inside eddy (global system) (PCR:p. 524)
|
||||
const vector r(cmptDivide(xp - position(n), sigma_));
|
||||
|
||||
if (mag(r) > 1)
|
||||
if (mag(r) >= scalar(1))
|
||||
{
|
||||
return vector::zero;
|
||||
}
|
||||
|
||||
// Relative position inside eddy (eddy principal system)
|
||||
const vector rp = Rpg_.T() & r;
|
||||
const vector rp(Rpg_.T() & r);
|
||||
|
||||
// Shape function (eddy principal system)
|
||||
const vector q = cmptMultiply(sigma_, vector::one - cmptMultiply(rp, rp));
|
||||
const vector q(cmptMultiply(sigma_, vector::one - cmptMultiply(rp, rp)));
|
||||
|
||||
// Fluctuating velocity (eddy principal system) (eq. 8)
|
||||
const vector uDashp = cmptMultiply(q, rp^alpha_);
|
||||
// Fluctuating velocity (eddy principal system) (PCR:Eq. 8)
|
||||
const vector uPrimep(cmptMultiply(q, rp^alpha_));
|
||||
|
||||
// Convert into global system (eq. 10)
|
||||
return c1_*(Rpg_ & uDashp);
|
||||
// Convert into global system (PCR:Eq. 10)
|
||||
return c1_*(Rpg_ & uPrimep);
|
||||
}
|
||||
|
||||
|
||||
@ -256,7 +257,7 @@ void Foam::eddy::writeCentreOBJ
|
||||
Ostream& os
|
||||
) const
|
||||
{
|
||||
point p = position(n);
|
||||
const point p(position(n));
|
||||
os << "v " << p.x() << " " << p.y() << " " << p.z() << nl;
|
||||
}
|
||||
|
||||
@ -295,14 +296,14 @@ Foam::label Foam::eddy::writeSurfaceOBJ
|
||||
x[nEddyPoints - 1] = - axisDir*s[dir1_];
|
||||
|
||||
label eddyPtI = 1;
|
||||
for (label axisI = 1; axisI < nFaceAxis; axisI++)
|
||||
for (label axisI = 1; axisI < nFaceAxis; ++axisI)
|
||||
{
|
||||
scalar z = s[dir1_]*cos(axisI*dPhi);
|
||||
scalar r = sqrt(sqr(s[dir2])*(1 - sqr(z)/sqr(s[dir1_])));
|
||||
const scalar z = s[dir1_]*cos(axisI*dPhi);
|
||||
const scalar r = sqrt(sqr(s[dir2])*(1 - sqr(z)/sqr(s[dir1_])));
|
||||
|
||||
for (label thetaI = 0; thetaI < nFaceTheta; thetaI++)
|
||||
for (label thetaI = 0; thetaI < nFaceTheta; ++thetaI)
|
||||
{
|
||||
scalar theta = thetaI*dTheta;
|
||||
const scalar theta = thetaI*dTheta;
|
||||
point& p = x[eddyPtI++];
|
||||
p[dir1_] = z;
|
||||
p[dir2] = r*sin(theta);
|
||||
@ -313,33 +314,33 @@ Foam::label Foam::eddy::writeSurfaceOBJ
|
||||
// Write points
|
||||
forAll(x, i)
|
||||
{
|
||||
point p = position(n) + (Rpg_ & x[i]);
|
||||
const point p = position(n) + (Rpg_ & x[i]);
|
||||
os << "v " << p.x() << " " << p.y() << " " << p.z() << nl;
|
||||
}
|
||||
|
||||
// Write the end cap tri faces
|
||||
for (label faceI = 0; faceI < nFaceTheta; faceI++)
|
||||
for (label faceI = 0; faceI < nFaceTheta; ++faceI)
|
||||
{
|
||||
label p1 = pointI + 1;
|
||||
label p2 = p1 + faceI + 1;
|
||||
const label p1 = pointI + 1;
|
||||
const label p2 = p1 + faceI + 1;
|
||||
label p3 = p2 + 1;
|
||||
if (faceI == nFaceTheta - 1) p3 -= nFaceTheta;
|
||||
os << "f " << p1 << " " << p2 << " " << p3 << nl;
|
||||
|
||||
label q1 = pointI + nEddyPoints;
|
||||
label q2 = q1 - faceI - 1;
|
||||
const label q1 = pointI + nEddyPoints;
|
||||
const label q2 = q1 - faceI - 1;
|
||||
label q3 = q2 - 1;
|
||||
if (faceI == nFaceTheta - 1) q3 += nFaceTheta;
|
||||
os << "f " << q1 << " " << q2 << " " << q3 << nl;
|
||||
}
|
||||
|
||||
// Write quad faces
|
||||
for (label axisI = 1; axisI < nFaceAxis - 1; axisI++)
|
||||
for (label axisI = 1; axisI < nFaceAxis - 1; ++axisI)
|
||||
{
|
||||
for (label thetaI = 0; thetaI < nFaceTheta; thetaI++)
|
||||
for (label thetaI = 0; thetaI < nFaceTheta; ++thetaI)
|
||||
{
|
||||
label p1 = pointI + 1 + (axisI - 1)*nFaceTheta + thetaI + 1;
|
||||
label p2 = p1 + nFaceTheta;
|
||||
const label p1 = pointI + 1 + (axisI - 1)*nFaceTheta + thetaI + 1;
|
||||
const label p2 = p1 + nFaceTheta;
|
||||
label p3 = p2 + 1;
|
||||
label p4 = p1 + 1;
|
||||
|
||||
|
||||
@ -6,7 +6,7 @@
|
||||
\\/ M anipulation |
|
||||
-------------------------------------------------------------------------------
|
||||
Copyright (C) 2015 OpenFOAM Foundation
|
||||
Copyright (C) 2016 OpenCFD Ltd.
|
||||
Copyright (C) 2016-2021 OpenCFD Ltd.
|
||||
-------------------------------------------------------------------------------
|
||||
License
|
||||
This file is part of OpenFOAM.
|
||||
@ -69,7 +69,7 @@ Ostream& operator<<(Ostream& os, const eddy& e);
|
||||
|
||||
class eddy
|
||||
{
|
||||
// Private data
|
||||
// Private Data
|
||||
|
||||
static label Gamma2Values[8];
|
||||
static UList<label> Gamma2;
|
||||
@ -83,7 +83,7 @@ class eddy
|
||||
//- Distance from reference position in normal direction
|
||||
scalar x_;
|
||||
|
||||
//- Length scales in 3-D space
|
||||
//- Integral-length scales in 3-D space
|
||||
vector sigma_;
|
||||
|
||||
//- Time-averaged intensity
|
||||
@ -133,14 +133,18 @@ public:
|
||||
const label patchFaceI, // patch face index
|
||||
const point& position0, // reference position
|
||||
const scalar x, // distance from reference position
|
||||
const scalar sigmaX, // length scale
|
||||
const symmTensor& R, // Stress tensor
|
||||
const scalar sigmaX, // integral-length scale
|
||||
const symmTensor& R, // Reynolds stress tensor
|
||||
Random& rndGen
|
||||
);
|
||||
|
||||
//- Construct copy
|
||||
//- Copy construct
|
||||
eddy(const eddy& e);
|
||||
|
||||
|
||||
// Public Data
|
||||
|
||||
//- Flag to activate debug statements
|
||||
static int debug;
|
||||
|
||||
|
||||
@ -149,26 +153,26 @@ public:
|
||||
// Access
|
||||
|
||||
//- Return the patch face index that spawned the eddy
|
||||
inline label patchFaceI() const;
|
||||
inline label patchFaceI() const noexcept;
|
||||
|
||||
//- Return the reference position
|
||||
inline const point& position0() const;
|
||||
inline const point& position0() const noexcept;
|
||||
|
||||
//- Return the distance from the reference position
|
||||
inline scalar x() const;
|
||||
inline scalar x() const noexcept;
|
||||
|
||||
//- Return the lLength scales in 3-D space
|
||||
inline const vector& sigma() const;
|
||||
//- Return the length scales in 3-D space
|
||||
inline const vector& sigma() const noexcept;
|
||||
|
||||
//- Return the time-averaged intensity
|
||||
inline const vector& alpha() const;
|
||||
inline const vector& alpha() const noexcept;
|
||||
|
||||
//- Return the coordinate system transformation from local
|
||||
// principal to global axes
|
||||
inline const tensor& Rpg() const;
|
||||
//- principal to global axes
|
||||
inline const tensor& Rpg() const noexcept;
|
||||
|
||||
//- Return the model coefficient c1
|
||||
inline scalar c1() const;
|
||||
inline scalar c1() const noexcept;
|
||||
|
||||
//- Return the eddy position
|
||||
inline point position(const vector& n) const;
|
||||
@ -192,10 +196,10 @@ public:
|
||||
inline boundBox bounds(const bool global = true) const;
|
||||
|
||||
|
||||
// Evaluate
|
||||
// Evaluation
|
||||
|
||||
//- Return the fluctuating velocity contribution at local point xp
|
||||
vector uDash(const point& xp, const vector& n) const;
|
||||
vector uPrime(const point& xp, const vector& n) const;
|
||||
|
||||
|
||||
// Writing
|
||||
|
||||
@ -6,7 +6,7 @@
|
||||
\\/ M anipulation |
|
||||
-------------------------------------------------------------------------------
|
||||
Copyright (C) 2015 OpenFOAM Foundation
|
||||
Copyright (C) 2016 OpenCFD Ltd.
|
||||
Copyright (C) 2016-2021 OpenCFD Ltd.
|
||||
-------------------------------------------------------------------------------
|
||||
License
|
||||
This file is part of OpenFOAM.
|
||||
@ -39,54 +39,54 @@ Foam::scalar Foam::eddy::epsi(Random& rndGen) const
|
||||
}
|
||||
|
||||
|
||||
inline Foam::label Foam::eddy::patchFaceI() const
|
||||
inline Foam::label Foam::eddy::patchFaceI() const noexcept
|
||||
{
|
||||
return patchFaceI_;
|
||||
}
|
||||
|
||||
|
||||
inline const Foam::point& Foam::eddy::position0() const
|
||||
inline const Foam::point& Foam::eddy::position0() const noexcept
|
||||
{
|
||||
return position0_;
|
||||
}
|
||||
|
||||
|
||||
inline Foam::scalar Foam::eddy::x() const
|
||||
inline Foam::scalar Foam::eddy::x() const noexcept
|
||||
{
|
||||
return x_;
|
||||
}
|
||||
|
||||
|
||||
inline const Foam::vector& Foam::eddy::sigma() const
|
||||
inline const Foam::vector& Foam::eddy::sigma() const noexcept
|
||||
{
|
||||
return sigma_;
|
||||
}
|
||||
|
||||
|
||||
inline const Foam::vector& Foam::eddy::alpha() const
|
||||
inline const Foam::vector& Foam::eddy::alpha() const noexcept
|
||||
{
|
||||
return alpha_;
|
||||
}
|
||||
|
||||
|
||||
inline const Foam::tensor& Foam::eddy::Rpg() const
|
||||
inline const Foam::tensor& Foam::eddy::Rpg() const noexcept
|
||||
{
|
||||
return Rpg_;
|
||||
}
|
||||
|
||||
|
||||
inline Foam::scalar Foam::eddy::c1() const noexcept
|
||||
{
|
||||
return c1_;
|
||||
}
|
||||
|
||||
|
||||
inline Foam::point Foam::eddy::position(const vector& n) const
|
||||
{
|
||||
return position0_ + n*x_;
|
||||
}
|
||||
|
||||
|
||||
inline Foam::scalar Foam::eddy::c1() const
|
||||
{
|
||||
return c1_;
|
||||
}
|
||||
|
||||
|
||||
Foam::vector Foam::eddy::epsilon(Random& rndGen) const
|
||||
{
|
||||
return vector(epsi(rndGen), epsi(rndGen), epsi(rndGen));
|
||||
|
||||
@ -6,7 +6,7 @@
|
||||
\\/ M anipulation |
|
||||
-------------------------------------------------------------------------------
|
||||
Copyright (C) 2015 OpenFOAM Foundation
|
||||
Copyright (C) 2016-2020 OpenCFD Ltd.
|
||||
Copyright (C) 2016-2021 OpenCFD Ltd.
|
||||
-------------------------------------------------------------------------------
|
||||
License
|
||||
This file is part of OpenFOAM.
|
||||
@ -27,13 +27,9 @@ License
|
||||
\*---------------------------------------------------------------------------*/
|
||||
|
||||
#include "turbulentDFSEMInletFvPatchVectorField.H"
|
||||
#include "volFields.H"
|
||||
#include "addToRunTimeSelectionTable.H"
|
||||
#include "fvPatchFieldMapper.H"
|
||||
#include "momentOfInertia.H"
|
||||
#include "OFstream.H"
|
||||
#include "globalIndex.H"
|
||||
#include "rawIOField.H"
|
||||
|
||||
// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
|
||||
|
||||
@ -51,7 +47,7 @@ void Foam::turbulentDFSEMInletFvPatchVectorField::writeEddyOBJ() const
|
||||
const labelList& boundaryPoints = pp.boundaryPoints();
|
||||
const pointField& localPoints = pp.localPoints();
|
||||
|
||||
vector offset = patchNormal_*maxSigmaX_;
|
||||
const vector offset(patchNormal_*maxSigmaX_);
|
||||
forAll(boundaryPoints, i)
|
||||
{
|
||||
point p = localPoints[boundaryPoints[i]];
|
||||
@ -65,24 +61,6 @@ void Foam::turbulentDFSEMInletFvPatchVectorField::writeEddyOBJ() const
|
||||
p -= offset;
|
||||
os << "v " << p.x() << " " << p.y() << " " << p.z() << nl;
|
||||
}
|
||||
|
||||
// Draw lines between points
|
||||
// Note: need to order to avoid crossing patch
|
||||
//const label nPoint = boundaryPoints.size();
|
||||
//
|
||||
//forAll(boundaryPoints, i)
|
||||
//{
|
||||
// label i1 = i;
|
||||
// label i2 = (i + 1) % nPoint;
|
||||
// os << "l " << i1 << " " << i2 << nl;
|
||||
//}
|
||||
//
|
||||
//forAll(boundaryPoints, i)
|
||||
//{
|
||||
// label i1 = i + nPoint;
|
||||
// label i2 = ((i + 1) % nPoint) + nPoint;
|
||||
// os << "l " << i1 << " " << i2 << nl;
|
||||
//}
|
||||
}
|
||||
|
||||
{
|
||||
@ -106,141 +84,31 @@ void Foam::turbulentDFSEMInletFvPatchVectorField::writeLumleyCoeffs() const
|
||||
{
|
||||
// Output list of xi vs eta
|
||||
|
||||
// Before interpolation/raw data
|
||||
if (interpolateR_)
|
||||
OFstream os(db().time().path()/"lumley_interpolated.out");
|
||||
|
||||
os << "# xi" << token::TAB << "eta" << endl;
|
||||
|
||||
const scalar t = db().time().timeOutputValue();
|
||||
const symmTensorField R(R_->value(t)/sqr(Uref_));
|
||||
|
||||
forAll(R, faceI)
|
||||
{
|
||||
const fileName valsFile
|
||||
(
|
||||
fileName
|
||||
(
|
||||
this->db().time().globalPath()
|
||||
/this->db().time().constant()
|
||||
/"boundaryData"
|
||||
/this->patch().name()
|
||||
/"0"
|
||||
/"R"
|
||||
)
|
||||
);
|
||||
// Normalised anisotropy tensor
|
||||
const symmTensor devR(dev(R[faceI]/(tr(R[faceI]))));
|
||||
|
||||
IOobject io
|
||||
(
|
||||
valsFile, // absolute path
|
||||
this->db().time(),
|
||||
IOobject::MUST_READ,
|
||||
IOobject::NO_WRITE,
|
||||
false, // no need to register
|
||||
true // is global object (currently not used)
|
||||
);
|
||||
// Second tensor invariant
|
||||
const scalar ii = min(0, invariantII(devR));
|
||||
|
||||
const rawIOField<symmTensor> Rexp(io, false);
|
||||
// Third tensor invariant
|
||||
const scalar iii = invariantIII(devR);
|
||||
|
||||
OFstream os(db().time().path()/"lumley_input.out");
|
||||
|
||||
os << "# xi" << token::TAB << "eta" << endl;
|
||||
|
||||
forAll(Rexp, faceI)
|
||||
{
|
||||
// Normalised anisotropy tensor
|
||||
symmTensor devR = dev(Rexp[faceI]/(tr(Rexp[faceI])));
|
||||
|
||||
// Second tensor invariant
|
||||
scalar ii = min(0, invariantII(devR));
|
||||
|
||||
// Third tensor invariant
|
||||
scalar iii = invariantIII(devR);
|
||||
|
||||
// xi, eta
|
||||
// See Pope - characterization of Reynolds-stress anisotropy
|
||||
scalar xi = cbrt(0.5*iii);
|
||||
scalar eta = sqrt(-ii/3.0);
|
||||
os << xi << token::TAB << eta << token::TAB
|
||||
<< ii << token::TAB << iii << endl;
|
||||
}
|
||||
// xi, eta
|
||||
// See Pope - characterization of Reynolds-stress anisotropy
|
||||
const scalar xi = cbrt(0.5*iii);
|
||||
const scalar eta = sqrt(-ii/3.0);
|
||||
os << xi << token::TAB << eta << token::TAB
|
||||
<< ii << token::TAB << iii << endl;
|
||||
}
|
||||
|
||||
// After interpolation
|
||||
{
|
||||
OFstream os(db().time().path()/"lumley_interpolated.out");
|
||||
|
||||
os << "# xi" << token::TAB << "eta" << endl;
|
||||
|
||||
forAll(R_, faceI)
|
||||
{
|
||||
// Normalised anisotropy tensor
|
||||
symmTensor devR = dev(R_[faceI]/(tr(R_[faceI])));
|
||||
|
||||
// Second tensor invariant
|
||||
scalar ii = min(0, invariantII(devR));
|
||||
|
||||
// Third tensor invariant
|
||||
scalar iii = invariantIII(devR);
|
||||
|
||||
// xi, eta
|
||||
// See Pope - characterization of Reynolds-stress anisotropy
|
||||
scalar xi = cbrt(0.5*iii);
|
||||
scalar eta = sqrt(-ii/3.0);
|
||||
os << xi << token::TAB << eta << token::TAB
|
||||
<< ii << token::TAB << iii << endl;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
const Foam::pointToPointPlanarInterpolation&
|
||||
Foam::turbulentDFSEMInletFvPatchVectorField::patchMapper() const
|
||||
{
|
||||
// Initialise interpolation (2D planar interpolation by triangulation)
|
||||
if (!mapperPtr_)
|
||||
{
|
||||
const fileName samplePointsFile
|
||||
(
|
||||
this->db().time().globalPath()
|
||||
/this->db().time().constant()
|
||||
/"boundaryData"
|
||||
/this->patch().name()
|
||||
/"points"
|
||||
);
|
||||
|
||||
IOobject io
|
||||
(
|
||||
samplePointsFile, // absolute path
|
||||
this->db().time(),
|
||||
IOobject::MUST_READ,
|
||||
IOobject::NO_WRITE,
|
||||
false, // no need to register
|
||||
true // is global object (currently not used)
|
||||
);
|
||||
|
||||
// Read data
|
||||
const rawIOField<point> samplePoints(io, false);
|
||||
|
||||
|
||||
DebugInFunction
|
||||
<< " Read " << samplePoints.size() << " sample points from "
|
||||
<< samplePointsFile << endl;
|
||||
|
||||
|
||||
// tbd: run-time selection
|
||||
bool nearestOnly =
|
||||
(
|
||||
!mapMethod_.empty()
|
||||
&& mapMethod_ != "planarInterpolation"
|
||||
);
|
||||
|
||||
// Allocate the interpolator
|
||||
mapperPtr_.reset
|
||||
(
|
||||
new pointToPointPlanarInterpolation
|
||||
(
|
||||
samplePoints,
|
||||
this->patch().patch().faceCentres(),
|
||||
perturb_,
|
||||
nearestOnly
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
return *mapperPtr_;
|
||||
}
|
||||
|
||||
|
||||
@ -252,7 +120,7 @@ void Foam::turbulentDFSEMInletFvPatchVectorField::initialisePatch()
|
||||
patchNormal_ = -gAverage(nf);
|
||||
|
||||
// Check that patch is planar
|
||||
scalar error = max(magSqr(patchNormal_ + nf));
|
||||
const scalar error = max(magSqr(patchNormal_ + nf));
|
||||
|
||||
if (error > SMALL)
|
||||
{
|
||||
@ -293,9 +161,9 @@ void Foam::turbulentDFSEMInletFvPatchVectorField::initialisePatch()
|
||||
}
|
||||
}
|
||||
|
||||
forAll(sumTriMagSf_, i)
|
||||
for (auto& s : sumTriMagSf_)
|
||||
{
|
||||
sumTriMagSf_[i] = 0.0;
|
||||
s = 0.0;
|
||||
}
|
||||
|
||||
sumTriMagSf_[Pstream::myProcNo() + 1] = sum(triMagSf);
|
||||
@ -303,7 +171,7 @@ void Foam::turbulentDFSEMInletFvPatchVectorField::initialisePatch()
|
||||
Pstream::listCombineGather(sumTriMagSf_, maxEqOp<scalar>());
|
||||
Pstream::listCombineScatter(sumTriMagSf_);
|
||||
|
||||
for (label i = 1; i < triMagSf.size(); i++)
|
||||
for (label i = 1; i < triMagSf.size(); ++i)
|
||||
{
|
||||
triMagSf[i] += triMagSf[i-1];
|
||||
}
|
||||
@ -314,7 +182,7 @@ void Foam::turbulentDFSEMInletFvPatchVectorField::initialisePatch()
|
||||
triCumulativeMagSf_.transfer(triMagSf);
|
||||
|
||||
// Convert sumTriMagSf_ into cumulative sum of areas per proc
|
||||
for (label i = 1; i < sumTriMagSf_.size(); i++)
|
||||
for (label i = 1; i < sumTriMagSf_.size(); ++i)
|
||||
{
|
||||
sumTriMagSf_[i] += sumTriMagSf_[i-1];
|
||||
}
|
||||
@ -336,7 +204,9 @@ void Foam::turbulentDFSEMInletFvPatchVectorField::initialiseEddyBox()
|
||||
{
|
||||
const scalarField& magSf = patch().magSf();
|
||||
|
||||
//const scalarField cellDx(Foam::sqrt(magSf));
|
||||
const scalarField L(L_->value(db().time().timeOutputValue())/Lref_);
|
||||
|
||||
// (PCF:Eq. 14)
|
||||
const scalarField cellDx(max(Foam::sqrt(magSf), 2/patch().deltaCoeffs()));
|
||||
|
||||
// Inialise eddy box extents
|
||||
@ -344,13 +214,10 @@ void Foam::turbulentDFSEMInletFvPatchVectorField::initialiseEddyBox()
|
||||
{
|
||||
scalar& s = sigmax_[faceI];
|
||||
|
||||
// Length scale in x direction (based on eq. 14)
|
||||
s = mag(L_[faceI]);
|
||||
s = min(s, kappa_*delta_);
|
||||
|
||||
// Allow eddies to be smaller than the mesh scale as suggested by
|
||||
// the reference?
|
||||
// s = min(s, nCellPerEddy_*cellDx[faceI]);
|
||||
// Average length scale (SST:Eq. 24)
|
||||
// Personal communication regarding (PCR:Eq. 14)
|
||||
// - the min operator in Eq. 14 is a typo, and should be a max operator
|
||||
s = min(mag(L[faceI]), kappa_*delta_);
|
||||
s = max(s, nCellPerEddy_*cellDx[faceI]);
|
||||
}
|
||||
|
||||
@ -383,7 +250,8 @@ Foam::pointIndexHit Foam::turbulentDFSEMInletFvPatchVectorField::setNewPosition
|
||||
|
||||
if (global)
|
||||
{
|
||||
scalar areaFraction = rndGen_.globalPosition<scalar>(0, patchArea_);
|
||||
const scalar areaFraction =
|
||||
rndGen_.globalPosition<scalar>(0, patchArea_);
|
||||
|
||||
// Determine which processor to use
|
||||
label procI = 0;
|
||||
@ -400,7 +268,7 @@ Foam::pointIndexHit Foam::turbulentDFSEMInletFvPatchVectorField::setNewPosition
|
||||
{
|
||||
// Find corresponding decomposed face triangle
|
||||
label triI = 0;
|
||||
scalar offset = sumTriMagSf_[procI];
|
||||
const scalar offset = sumTriMagSf_[procI];
|
||||
forAllReverse(triCumulativeMagSf_, i)
|
||||
{
|
||||
if (areaFraction > triCumulativeMagSf_[i] + offset)
|
||||
@ -423,8 +291,8 @@ Foam::pointIndexHit Foam::turbulentDFSEMInletFvPatchVectorField::setNewPosition
|
||||
{
|
||||
// Find corresponding decomposed face triangle on local processor
|
||||
label triI = 0;
|
||||
scalar maxAreaLimit = triCumulativeMagSf_.last();
|
||||
scalar areaFraction = rndGen_.position<scalar>(0, maxAreaLimit);
|
||||
const scalar maxAreaLimit = triCumulativeMagSf_.last();
|
||||
const scalar areaFraction = rndGen_.position<scalar>(0, maxAreaLimit);
|
||||
|
||||
forAllReverse(triCumulativeMagSf_, i)
|
||||
{
|
||||
@ -450,6 +318,9 @@ Foam::pointIndexHit Foam::turbulentDFSEMInletFvPatchVectorField::setNewPosition
|
||||
|
||||
void Foam::turbulentDFSEMInletFvPatchVectorField::initialiseEddies()
|
||||
{
|
||||
const scalar t = db().time().timeOutputValue();
|
||||
const symmTensorField R(R_->value(t)/sqr(Uref_));
|
||||
|
||||
DynamicList<eddy> eddies(size());
|
||||
|
||||
// Initialise eddy properties
|
||||
@ -465,18 +336,18 @@ void Foam::turbulentDFSEMInletFvPatchVectorField::initialiseEddies()
|
||||
{
|
||||
// Get new parallel consistent position
|
||||
pointIndexHit pos(setNewPosition(true));
|
||||
label faceI = pos.index();
|
||||
const label patchFaceI = pos.index();
|
||||
|
||||
// Note: only 1 processor will pick up this face
|
||||
if (faceI != -1)
|
||||
if (patchFaceI != -1)
|
||||
{
|
||||
eddy e
|
||||
(
|
||||
faceI,
|
||||
patchFaceI,
|
||||
pos.hitPoint(),
|
||||
rndGen_.position<scalar>(-maxSigmaX_, maxSigmaX_),
|
||||
sigmax_[faceI],
|
||||
R_[faceI],
|
||||
sigmax_[patchFaceI],
|
||||
R[patchFaceI],
|
||||
rndGen_
|
||||
);
|
||||
|
||||
@ -526,16 +397,21 @@ void Foam::turbulentDFSEMInletFvPatchVectorField::initialiseEddies()
|
||||
WarningInFunction
|
||||
<< "Patch: " << patch().patch().name()
|
||||
<< " on field " << internalField().name()
|
||||
<< ": No eddies seeded - please check your set-up" << endl;
|
||||
<< ": No eddies seeded - please check your set-up"
|
||||
<< endl;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void Foam::turbulentDFSEMInletFvPatchVectorField::convectEddies
|
||||
(
|
||||
const vector& UBulk,
|
||||
const scalar deltaT
|
||||
)
|
||||
{
|
||||
const scalar t = db().time().timeOutputValue();
|
||||
const symmTensorField R(R_->value(t)/sqr(Uref_));
|
||||
|
||||
// Note: all operations applied to local processor only
|
||||
|
||||
label nRecycled = 0;
|
||||
@ -543,7 +419,7 @@ void Foam::turbulentDFSEMInletFvPatchVectorField::convectEddies
|
||||
forAll(eddies_, eddyI)
|
||||
{
|
||||
eddy& e = eddies_[eddyI];
|
||||
e.move(deltaT*(UMean_ & patchNormal_));
|
||||
e.move(deltaT*(UBulk & patchNormal_));
|
||||
|
||||
const scalar position0 = e.x();
|
||||
|
||||
@ -555,17 +431,17 @@ void Foam::turbulentDFSEMInletFvPatchVectorField::convectEddies
|
||||
|
||||
while (search && iter++ < seedIterMax_)
|
||||
{
|
||||
// Spawn new eddy with new random properties (intensity etc)
|
||||
pointIndexHit pos(setNewPosition(false));
|
||||
label faceI = pos.index();
|
||||
// Spawn new eddy with new random properties (intensity etc)
|
||||
pointIndexHit pos(setNewPosition(false));
|
||||
const label patchFaceI = pos.index();
|
||||
|
||||
e = eddy
|
||||
e = eddy
|
||||
(
|
||||
faceI,
|
||||
patchFaceI,
|
||||
pos.hitPoint(),
|
||||
position0 - floor(position0/maxSigmaX_)*maxSigmaX_,
|
||||
sigmax_[faceI],
|
||||
R_[faceI],
|
||||
sigmax_[patchFaceI],
|
||||
R[patchFaceI],
|
||||
rndGen_
|
||||
);
|
||||
|
||||
@ -583,27 +459,28 @@ void Foam::turbulentDFSEMInletFvPatchVectorField::convectEddies
|
||||
|
||||
if (debug && nRecycled > 0)
|
||||
{
|
||||
Info<< "Patch: " << patch().patch().name() << " recycled "
|
||||
<< nRecycled << " eddies" << endl;
|
||||
Info<< "Patch: " << patch().patch().name()
|
||||
<< " recycled " << nRecycled << " eddies"
|
||||
<< endl;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Foam::vector Foam::turbulentDFSEMInletFvPatchVectorField::uDashEddy
|
||||
Foam::vector Foam::turbulentDFSEMInletFvPatchVectorField::uPrimeEddy
|
||||
(
|
||||
const List<eddy>& eddies,
|
||||
const point& patchFaceCf
|
||||
) const
|
||||
{
|
||||
vector uDash(Zero);
|
||||
vector uPrime(Zero);
|
||||
|
||||
forAll(eddies, k)
|
||||
{
|
||||
const eddy& e = eddies[k];
|
||||
uDash += e.uDash(patchFaceCf, patchNormal_);
|
||||
uPrime += e.uPrime(patchFaceCf, patchNormal_);
|
||||
}
|
||||
|
||||
return uDash;
|
||||
return uPrime;
|
||||
}
|
||||
|
||||
|
||||
@ -629,8 +506,8 @@ void Foam::turbulentDFSEMInletFvPatchVectorField::calcOverlappingProcEddies
|
||||
const eddy& e = eddies_[i];
|
||||
|
||||
// Eddy bounds
|
||||
point x = e.position(patchNormal_);
|
||||
boundBox ebb = e.bounds();
|
||||
const point x(e.position(patchNormal_));
|
||||
boundBox ebb(e.bounds());
|
||||
ebb.min() += x;
|
||||
ebb.max() += x;
|
||||
|
||||
@ -678,10 +555,10 @@ void Foam::turbulentDFSEMInletFvPatchVectorField::calcOverlappingProcEddies
|
||||
if (procI != Pstream::myProcNo())
|
||||
{
|
||||
// What I need to receive is what other processor is sending to me
|
||||
label nRecv = sendSizes[procI][Pstream::myProcNo()];
|
||||
const label nRecv = sendSizes[procI][Pstream::myProcNo()];
|
||||
constructMap[procI].setSize(nRecv);
|
||||
|
||||
for (label i = 0; i < nRecv; i++)
|
||||
for (label i = 0; i < nRecv; ++i)
|
||||
{
|
||||
constructMap[procI][i] = segmentI++;
|
||||
}
|
||||
@ -738,37 +615,33 @@ turbulentDFSEMInletFvPatchVectorField
|
||||
)
|
||||
:
|
||||
fixedValueFvPatchField<vector>(p, iF),
|
||||
delta_(Zero),
|
||||
d_(Zero),
|
||||
kappa_(Zero),
|
||||
|
||||
perturb_(1e-5),
|
||||
mapMethod_("nearestCell"),
|
||||
mapperPtr_(nullptr),
|
||||
interpolateR_(false),
|
||||
interpolateL_(false),
|
||||
interpolateU_(false),
|
||||
R_(),
|
||||
L_(),
|
||||
U_(),
|
||||
UMean_(Zero),
|
||||
U_(nullptr),
|
||||
R_(nullptr),
|
||||
L_(nullptr),
|
||||
delta_(1.0),
|
||||
d_(1.0),
|
||||
kappa_(0.41),
|
||||
Uref_(1.0),
|
||||
Lref_(1.0),
|
||||
scale_(1.0),
|
||||
m_(0.5),
|
||||
nCellPerEddy_(5),
|
||||
|
||||
patchArea_(-1),
|
||||
triFace_(),
|
||||
triToFace_(),
|
||||
triCumulativeMagSf_(),
|
||||
sumTriMagSf_(Pstream::nProcs() + 1, Zero),
|
||||
patchNormal_(Zero),
|
||||
patchBounds_(boundBox::invertedBox),
|
||||
|
||||
eddies_(Zero),
|
||||
nCellPerEddy_(5),
|
||||
patchNormal_(Zero),
|
||||
v0_(Zero),
|
||||
rndGen_(Pstream::myProcNo()),
|
||||
sigmax_(size(), Zero),
|
||||
maxSigmaX_(Zero),
|
||||
nEddy_(Zero),
|
||||
nEddy_(0),
|
||||
curTimeIndex_(-1),
|
||||
patchBounds_(boundBox::invertedBox),
|
||||
singleProc_(false),
|
||||
writeEddies_(false)
|
||||
{}
|
||||
@ -784,37 +657,33 @@ turbulentDFSEMInletFvPatchVectorField
|
||||
)
|
||||
:
|
||||
fixedValueFvPatchField<vector>(ptf, p, iF, mapper),
|
||||
U_(ptf.U_.clone(patch().patch())),
|
||||
R_(ptf.R_.clone(patch().patch())),
|
||||
L_(ptf.L_.clone(patch().patch())),
|
||||
delta_(ptf.delta_),
|
||||
d_(ptf.d_),
|
||||
kappa_(ptf.kappa_),
|
||||
|
||||
perturb_(ptf.perturb_),
|
||||
mapMethod_(ptf.mapMethod_),
|
||||
mapperPtr_(nullptr),
|
||||
interpolateR_(ptf.interpolateR_),
|
||||
interpolateL_(ptf.interpolateL_),
|
||||
interpolateU_(ptf.interpolateU_),
|
||||
R_(ptf.R_, mapper),
|
||||
L_(ptf.L_, mapper),
|
||||
U_(ptf.U_, mapper),
|
||||
UMean_(ptf.UMean_),
|
||||
Uref_(ptf.Uref_),
|
||||
Lref_(ptf.Lref_),
|
||||
scale_(ptf.scale_),
|
||||
m_(ptf.m_),
|
||||
nCellPerEddy_(ptf.nCellPerEddy_),
|
||||
|
||||
patchArea_(ptf.patchArea_),
|
||||
triFace_(ptf.triFace_),
|
||||
triToFace_(ptf.triToFace_),
|
||||
triCumulativeMagSf_(ptf.triCumulativeMagSf_),
|
||||
sumTriMagSf_(ptf.sumTriMagSf_),
|
||||
patchNormal_(ptf.patchNormal_),
|
||||
patchBounds_(ptf.patchBounds_),
|
||||
|
||||
eddies_(ptf.eddies_),
|
||||
nCellPerEddy_(ptf.nCellPerEddy_),
|
||||
patchNormal_(ptf.patchNormal_),
|
||||
v0_(ptf.v0_),
|
||||
rndGen_(ptf.rndGen_),
|
||||
sigmax_(ptf.sigmax_, mapper),
|
||||
maxSigmaX_(ptf.maxSigmaX_),
|
||||
nEddy_(Zero),
|
||||
nEddy_(ptf.nEddy_),
|
||||
curTimeIndex_(-1),
|
||||
patchBounds_(ptf.patchBounds_),
|
||||
singleProc_(ptf.singleProc_),
|
||||
writeEddies_(ptf.writeEddies_)
|
||||
{}
|
||||
@ -829,46 +698,42 @@ turbulentDFSEMInletFvPatchVectorField
|
||||
)
|
||||
:
|
||||
fixedValueFvPatchField<vector>(p, iF, dict),
|
||||
delta_(dict.get<scalar>("delta")),
|
||||
d_(dict.getOrDefault<scalar>("d", 1)),
|
||||
kappa_(dict.getOrDefault<scalar>("kappa", 0.41)),
|
||||
|
||||
perturb_(dict.getOrDefault<scalar>("perturb", 1e-5)),
|
||||
mapMethod_(dict.getOrDefault<word>("mapMethod", "nearestCell")),
|
||||
mapperPtr_(nullptr),
|
||||
interpolateR_(dict.getOrDefault("interpolateR", false)),
|
||||
interpolateL_(dict.getOrDefault("interpolateL", false)),
|
||||
interpolateU_(dict.getOrDefault("interpolateU", false)),
|
||||
R_(interpolateOrRead<symmTensor>("R", dict, interpolateR_)),
|
||||
L_(interpolateOrRead<scalar>("L", dict, interpolateL_)),
|
||||
U_(interpolateOrRead<vector>("U", dict, interpolateU_)),
|
||||
UMean_(Zero),
|
||||
U_(PatchFunction1<vector>::New(patch().patch(), "U", dict)),
|
||||
R_(PatchFunction1<symmTensor>::New(patch().patch(), "R", dict)),
|
||||
L_(PatchFunction1<scalar>::New(patch().patch(), "L", dict)),
|
||||
delta_(dict.getCheck<scalar>("delta", scalarMinMax::ge(0))),
|
||||
d_(dict.getCheckOrDefault<scalar>("d", 1, scalarMinMax::ge(SMALL))),
|
||||
kappa_(dict.getCheckOrDefault<scalar>("kappa", 0.41, scalarMinMax::ge(0))),
|
||||
Uref_(dict.getCheckOrDefault<scalar>("Uref", 1, scalarMinMax::ge(SMALL))),
|
||||
Lref_(dict.getCheckOrDefault<scalar>("Lref", 1, scalarMinMax::ge(SMALL))),
|
||||
scale_(dict.getCheckOrDefault<scalar>("scale", 1, scalarMinMax::ge(0))),
|
||||
m_(dict.getCheckOrDefault<scalar>("m", 0.5, scalarMinMax::ge(0))),
|
||||
nCellPerEddy_(dict.getOrDefault<label>("nCellPerEddy", 5)),
|
||||
|
||||
patchArea_(-1),
|
||||
triFace_(),
|
||||
triToFace_(),
|
||||
triCumulativeMagSf_(),
|
||||
sumTriMagSf_(Pstream::nProcs() + 1, Zero),
|
||||
patchNormal_(Zero),
|
||||
patchBounds_(boundBox::invertedBox),
|
||||
|
||||
eddies_(),
|
||||
nCellPerEddy_(dict.getOrDefault<label>("nCellPerEddy", 5)),
|
||||
patchNormal_(Zero),
|
||||
v0_(Zero),
|
||||
rndGen_(),
|
||||
sigmax_(size(), Zero),
|
||||
maxSigmaX_(Zero),
|
||||
nEddy_(Zero),
|
||||
nEddy_(0),
|
||||
curTimeIndex_(-1),
|
||||
patchBounds_(boundBox::invertedBox),
|
||||
singleProc_(false),
|
||||
writeEddies_(dict.getOrDefault("writeEddies", false))
|
||||
{
|
||||
eddy::debug = debug;
|
||||
|
||||
checkStresses(R_);
|
||||
const scalar t = db().time().timeOutputValue();
|
||||
const symmTensorField R(R_->value(t)/sqr(Uref_));
|
||||
|
||||
// Set UMean as patch area average value
|
||||
UMean_ = gSum(U_*patch().magSf())/(gSum(patch().magSf()) + ROOTVSMALL);
|
||||
checkStresses(R);
|
||||
}
|
||||
|
||||
|
||||
@ -879,37 +744,33 @@ turbulentDFSEMInletFvPatchVectorField
|
||||
)
|
||||
:
|
||||
fixedValueFvPatchField<vector>(ptf),
|
||||
U_(ptf.U_.clone(patch().patch())),
|
||||
R_(ptf.R_.clone(patch().patch())),
|
||||
L_(ptf.L_.clone(patch().patch())),
|
||||
delta_(ptf.delta_),
|
||||
d_(ptf.d_),
|
||||
kappa_(ptf.kappa_),
|
||||
|
||||
perturb_(ptf.perturb_),
|
||||
mapMethod_(ptf.mapMethod_),
|
||||
mapperPtr_(nullptr),
|
||||
interpolateR_(ptf.interpolateR_),
|
||||
interpolateL_(ptf.interpolateL_),
|
||||
interpolateU_(ptf.interpolateU_),
|
||||
R_(ptf.R_),
|
||||
L_(ptf.L_),
|
||||
U_(ptf.U_),
|
||||
UMean_(ptf.UMean_),
|
||||
Uref_(ptf.Uref_),
|
||||
Lref_(ptf.Lref_),
|
||||
scale_(ptf.scale_),
|
||||
m_(ptf.m_),
|
||||
nCellPerEddy_(ptf.nCellPerEddy_),
|
||||
|
||||
patchArea_(ptf.patchArea_),
|
||||
triFace_(ptf.triFace_),
|
||||
triToFace_(ptf.triToFace_),
|
||||
triCumulativeMagSf_(ptf.triCumulativeMagSf_),
|
||||
sumTriMagSf_(ptf.sumTriMagSf_),
|
||||
patchNormal_(ptf.patchNormal_),
|
||||
patchBounds_(ptf.patchBounds_),
|
||||
|
||||
eddies_(ptf.eddies_),
|
||||
nCellPerEddy_(ptf.nCellPerEddy_),
|
||||
patchNormal_(ptf.patchNormal_),
|
||||
v0_(ptf.v0_),
|
||||
rndGen_(ptf.rndGen_),
|
||||
sigmax_(ptf.sigmax_),
|
||||
maxSigmaX_(ptf.maxSigmaX_),
|
||||
nEddy_(Zero),
|
||||
nEddy_(ptf.nEddy_),
|
||||
curTimeIndex_(-1),
|
||||
patchBounds_(ptf.patchBounds_),
|
||||
singleProc_(ptf.singleProc_),
|
||||
writeEddies_(ptf.writeEddies_)
|
||||
{}
|
||||
@ -923,37 +784,33 @@ turbulentDFSEMInletFvPatchVectorField
|
||||
)
|
||||
:
|
||||
fixedValueFvPatchField<vector>(ptf, iF),
|
||||
U_(ptf.U_.clone(patch().patch())),
|
||||
R_(ptf.R_.clone(patch().patch())),
|
||||
L_(ptf.L_.clone(patch().patch())),
|
||||
delta_(ptf.delta_),
|
||||
d_(ptf.d_),
|
||||
kappa_(ptf.kappa_),
|
||||
|
||||
perturb_(ptf.perturb_),
|
||||
mapMethod_(ptf.mapMethod_),
|
||||
mapperPtr_(nullptr),
|
||||
interpolateR_(ptf.interpolateR_),
|
||||
interpolateL_(ptf.interpolateL_),
|
||||
interpolateU_(ptf.interpolateU_),
|
||||
R_(ptf.R_),
|
||||
L_(ptf.L_),
|
||||
U_(ptf.U_),
|
||||
UMean_(ptf.UMean_),
|
||||
Uref_(ptf.Uref_),
|
||||
Lref_(ptf.Lref_),
|
||||
scale_(ptf.scale_),
|
||||
m_(ptf.m_),
|
||||
nCellPerEddy_(ptf.nCellPerEddy_),
|
||||
|
||||
patchArea_(ptf.patchArea_),
|
||||
triFace_(ptf.triFace_),
|
||||
triToFace_(ptf.triToFace_),
|
||||
triCumulativeMagSf_(ptf.triCumulativeMagSf_),
|
||||
sumTriMagSf_(ptf.sumTriMagSf_),
|
||||
patchNormal_(ptf.patchNormal_),
|
||||
patchBounds_(ptf.patchBounds_),
|
||||
|
||||
eddies_(ptf.eddies_),
|
||||
nCellPerEddy_(ptf.nCellPerEddy_),
|
||||
patchNormal_(ptf.patchNormal_),
|
||||
v0_(ptf.v0_),
|
||||
rndGen_(ptf.rndGen_),
|
||||
sigmax_(ptf.sigmax_),
|
||||
maxSigmaX_(ptf.maxSigmaX_),
|
||||
nEddy_(Zero),
|
||||
nEddy_(ptf.nEddy_),
|
||||
curTimeIndex_(-1),
|
||||
patchBounds_(ptf.patchBounds_),
|
||||
singleProc_(ptf.singleProc_),
|
||||
writeEddies_(ptf.writeEddies_)
|
||||
{}
|
||||
@ -981,11 +838,11 @@ bool Foam::turbulentDFSEMInletFvPatchVectorField::checkStresses
|
||||
<< exit(FatalError);
|
||||
}
|
||||
|
||||
scalar a_xx = sqrt(R.xx());
|
||||
const scalar a_xx = sqrt(R.xx());
|
||||
|
||||
scalar a_xy = R.xy()/a_xx;
|
||||
const scalar a_xy = R.xy()/a_xx;
|
||||
|
||||
scalar a_yy_2 = R.yy() - sqr(a_xy);
|
||||
const scalar a_yy_2 = R.yy() - sqr(a_xy);
|
||||
|
||||
if (a_yy_2 < 0)
|
||||
{
|
||||
@ -996,13 +853,13 @@ bool Foam::turbulentDFSEMInletFvPatchVectorField::checkStresses
|
||||
<< exit(FatalError);
|
||||
}
|
||||
|
||||
scalar a_yy = Foam::sqrt(a_yy_2);
|
||||
const scalar a_yy = Foam::sqrt(a_yy_2);
|
||||
|
||||
scalar a_xz = R.xz()/a_xx;
|
||||
const scalar a_xz = R.xz()/a_xx;
|
||||
|
||||
scalar a_yz = (R.yz() - a_xy*a_xz)*a_yy;
|
||||
const scalar a_yz = (R.yz() - a_xy*a_xz)/a_yy;
|
||||
|
||||
scalar a_zz_2 = R.zz() - sqr(a_xz) - sqr(a_yz);
|
||||
const scalar a_zz_2 = R.zz() - sqr(a_xz) - sqr(a_yz);
|
||||
|
||||
if (a_zz_2 < 0)
|
||||
{
|
||||
@ -1013,7 +870,7 @@ bool Foam::turbulentDFSEMInletFvPatchVectorField::checkStresses
|
||||
<< exit(FatalError);
|
||||
}
|
||||
|
||||
scalar a_zz = Foam::sqrt(a_zz_2);
|
||||
const scalar a_zz = Foam::sqrt(a_zz_2);
|
||||
|
||||
if (debug)
|
||||
{
|
||||
@ -1036,11 +893,18 @@ void Foam::turbulentDFSEMInletFvPatchVectorField::autoMap
|
||||
{
|
||||
fixedValueFvPatchField<vector>::autoMap(m);
|
||||
|
||||
// Clear interpolator
|
||||
mapperPtr_.clear();
|
||||
R_.autoMap(m);
|
||||
L_.autoMap(m);
|
||||
U_.autoMap(m);
|
||||
if (U_)
|
||||
{
|
||||
U_->autoMap(m);
|
||||
}
|
||||
if (R_)
|
||||
{
|
||||
R_->autoMap(m);
|
||||
}
|
||||
if (L_)
|
||||
{
|
||||
L_->autoMap(m);
|
||||
}
|
||||
|
||||
sigmax_.autoMap(m);
|
||||
}
|
||||
@ -1054,15 +918,21 @@ void Foam::turbulentDFSEMInletFvPatchVectorField::rmap
|
||||
{
|
||||
fixedValueFvPatchField<vector>::rmap(ptf, addr);
|
||||
|
||||
const turbulentDFSEMInletFvPatchVectorField& dfsemptf =
|
||||
const auto& dfsemptf =
|
||||
refCast<const turbulentDFSEMInletFvPatchVectorField>(ptf);
|
||||
|
||||
R_.rmap(dfsemptf.R_, addr);
|
||||
L_.rmap(dfsemptf.L_, addr);
|
||||
U_.rmap(dfsemptf.U_, addr);
|
||||
|
||||
// Clear interpolator
|
||||
mapperPtr_.clear();
|
||||
if (U_)
|
||||
{
|
||||
U_->rmap(dfsemptf.U_(), addr);
|
||||
}
|
||||
if (R_)
|
||||
{
|
||||
R_->rmap(dfsemptf.R_(), addr);
|
||||
}
|
||||
if (L_)
|
||||
{
|
||||
L_->rmap(dfsemptf.L_(), addr);
|
||||
}
|
||||
|
||||
sigmax_.rmap(dfsemptf.sigmax_, addr);
|
||||
}
|
||||
@ -1087,38 +957,38 @@ void Foam::turbulentDFSEMInletFvPatchVectorField::updateCoeffs()
|
||||
|
||||
if (curTimeIndex_ != db().time().timeIndex())
|
||||
{
|
||||
if (debug)
|
||||
{
|
||||
label n = eddies_.size();
|
||||
Info<< "Number of eddies: " << returnReduce(n, sumOp<label>())
|
||||
<< endl;
|
||||
}
|
||||
tmp<vectorField> UMean =
|
||||
U_->value(db().time().timeOutputValue())/Uref_;
|
||||
|
||||
// (PCR:p. 522)
|
||||
const vector UBulk
|
||||
(
|
||||
gSum(UMean()*patch().magSf())
|
||||
/(gSum(patch().magSf()) + ROOTVSMALL)
|
||||
);
|
||||
|
||||
// Move eddies using bulk velocity
|
||||
const scalar deltaT = db().time().deltaTValue();
|
||||
convectEddies(UBulk, deltaT);
|
||||
|
||||
// Move eddies using mean velocity
|
||||
convectEddies(deltaT);
|
||||
|
||||
// Set velocity
|
||||
// Set mean velocity
|
||||
vectorField& U = *this;
|
||||
//U = UMean_;
|
||||
U = U_;
|
||||
|
||||
const pointField& Cf = patch().Cf();
|
||||
U = UMean;
|
||||
|
||||
// Apply second part of normalisation coefficient
|
||||
// Note: factor of 2 required to match reference stresses?
|
||||
const scalar FACTOR = 2;
|
||||
const scalar c = FACTOR*Foam::sqrt(10*v0_)/Foam::sqrt(scalar(nEddy_));
|
||||
const scalar c =
|
||||
scale_*Foam::pow(10*v0_, m_)/Foam::sqrt(scalar(nEddy_));
|
||||
|
||||
// In parallel, need to collect all eddies that will interact with
|
||||
// local faces
|
||||
|
||||
const pointField& Cf = patch().Cf();
|
||||
|
||||
if (singleProc_ || !Pstream::parRun())
|
||||
{
|
||||
forAll(U, faceI)
|
||||
{
|
||||
U[faceI] += c*uDashEddy(eddies_, Cf[faceI]);
|
||||
U[faceI] += c*uPrimeEddy(eddies_, Cf[faceI]);
|
||||
}
|
||||
}
|
||||
else
|
||||
@ -1126,7 +996,7 @@ void Foam::turbulentDFSEMInletFvPatchVectorField::updateCoeffs()
|
||||
// Process local eddy contributions
|
||||
forAll(U, faceI)
|
||||
{
|
||||
U[faceI] += c*uDashEddy(eddies_, Cf[faceI]);
|
||||
U[faceI] += c*uPrimeEddy(eddies_, Cf[faceI]);
|
||||
}
|
||||
|
||||
// Add contributions from overlapping eddies
|
||||
@ -1139,30 +1009,21 @@ void Foam::turbulentDFSEMInletFvPatchVectorField::updateCoeffs()
|
||||
|
||||
if (eddies.size())
|
||||
{
|
||||
//Pout<< "Applying " << eddies.size()
|
||||
// << " eddies from processor " << procI << endl;
|
||||
|
||||
forAll(U, faceI)
|
||||
{
|
||||
U[faceI] += c*uDashEddy(eddies, Cf[faceI]);
|
||||
U[faceI] += c*uPrimeEddy(eddies, Cf[faceI]);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Re-scale to ensure correct flow rate
|
||||
scalar fCorr =
|
||||
gSum((UMean_ & patchNormal_)*patch().magSf())
|
||||
const scalar fCorr =
|
||||
gSum((UBulk & patchNormal_)*patch().magSf())
|
||||
/gSum(U & -patch().Sf());
|
||||
|
||||
U *= fCorr;
|
||||
|
||||
if (debug)
|
||||
{
|
||||
Info<< "Patch:" << patch().patch().name()
|
||||
<< " min/max(U):" << gMin(U) << ", " << gMax(U) << endl;
|
||||
}
|
||||
|
||||
curTimeIndex_ = db().time().timeIndex();
|
||||
|
||||
if (writeEddies_)
|
||||
@ -1170,9 +1031,22 @@ void Foam::turbulentDFSEMInletFvPatchVectorField::updateCoeffs()
|
||||
writeEddyOBJ();
|
||||
}
|
||||
|
||||
if (debug && db().time().writeTime())
|
||||
if (debug)
|
||||
{
|
||||
writeLumleyCoeffs();
|
||||
Info<< "Magnitude of bulk velocity: " << UBulk << endl;
|
||||
|
||||
label n = eddies_.size();
|
||||
Info<< "Number of eddies: " << returnReduce(n, sumOp<label>())
|
||||
<< endl;
|
||||
|
||||
Info<< "Patch:" << patch().patch().name()
|
||||
<< " min/max(U):" << gMin(U) << ", " << gMax(U)
|
||||
<< endl;
|
||||
|
||||
if (db().time().writeTime())
|
||||
{
|
||||
writeLumleyCoeffs();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -1183,38 +1057,28 @@ void Foam::turbulentDFSEMInletFvPatchVectorField::updateCoeffs()
|
||||
void Foam::turbulentDFSEMInletFvPatchVectorField::write(Ostream& os) const
|
||||
{
|
||||
fvPatchField<vector>::write(os);
|
||||
writeEntry("value", os);
|
||||
os.writeEntry("delta", delta_);
|
||||
os.writeEntryIfDifferent<scalar>("d", 1.0, d_);
|
||||
os.writeEntryIfDifferent<scalar>("kappa", 0.41, kappa_);
|
||||
os.writeEntryIfDifferent<scalar>("perturb", 1e-5, perturb_);
|
||||
os.writeEntryIfDifferent<scalar>("Uref", 1.0, Uref_);
|
||||
os.writeEntryIfDifferent<scalar>("Lref", 1.0, Lref_);
|
||||
os.writeEntryIfDifferent<scalar>("scale", 1.0, scale_);
|
||||
os.writeEntryIfDifferent<scalar>("m", 0.5, m_);
|
||||
os.writeEntryIfDifferent<label>("nCellPerEddy", 5, nCellPerEddy_);
|
||||
os.writeEntryIfDifferent("writeEddies", false, writeEddies_);
|
||||
|
||||
if (!interpolateR_)
|
||||
if (U_)
|
||||
{
|
||||
R_.writeEntry("R", os);
|
||||
U_->writeData(os);
|
||||
}
|
||||
|
||||
if (!interpolateL_)
|
||||
if (R_)
|
||||
{
|
||||
L_.writeEntry("L", os);
|
||||
R_->writeData(os);
|
||||
}
|
||||
|
||||
if (!interpolateU_)
|
||||
if (L_)
|
||||
{
|
||||
U_.writeEntry("U", os);
|
||||
}
|
||||
|
||||
if (!mapMethod_.empty())
|
||||
{
|
||||
os.writeEntryIfDifferent<word>
|
||||
(
|
||||
"mapMethod",
|
||||
"nearestCell",
|
||||
mapMethod_
|
||||
);
|
||||
L_->writeData(os);
|
||||
}
|
||||
writeEntry("value", os);
|
||||
}
|
||||
|
||||
|
||||
|
||||
@ -6,7 +6,7 @@
|
||||
\\/ M anipulation |
|
||||
-------------------------------------------------------------------------------
|
||||
Copyright (C) 2015 OpenFOAM Foundation
|
||||
Copyright (C) 2016-2019 OpenCFD Ltd.
|
||||
Copyright (C) 2016-2021 OpenCFD Ltd.
|
||||
-------------------------------------------------------------------------------
|
||||
License
|
||||
This file is part of OpenFOAM.
|
||||
@ -31,56 +31,107 @@ Group
|
||||
grpInletBoundaryConditions
|
||||
|
||||
Description
|
||||
Velocity boundary condition including synthesised eddies for use with LES
|
||||
and DES turbulent flows.
|
||||
The \c turbulentDFSEMInlet is a synthesised-eddy based velocity inlet
|
||||
boundary condition to generate synthetic turbulence-alike time-series
|
||||
from a given set of turbulence statistics for LES and hybrid RANS-LES
|
||||
computations.
|
||||
|
||||
Reference:
|
||||
\verbatim
|
||||
Poletto, R., Craft, T., & Revell, A. (2013).
|
||||
A new divergence free synthetic eddy method for
|
||||
the reproduction of inlet flow conditions for LES.
|
||||
Flow, turbulence and combustion, 91(3), 519-539.
|
||||
DOI:10.1007/s10494-013-9488-2
|
||||
\endverbatim
|
||||
Standard model (tag:PCR):
|
||||
Poletto, R., Craft, T., & Revell, A. (2013).
|
||||
A new divergence free synthetic eddy method for
|
||||
the reproduction of inlet flow conditions for LES.
|
||||
Flow, turbulence and combustion, 91(3), 519-539.
|
||||
DOI:10.1007/s10494-013-9488-2
|
||||
|
||||
Reynolds stress, velocity and turbulence length scale values can either
|
||||
be specified directly, or mapped. If mapping, the values should be
|
||||
entered in the same form as the \c timeVaryingMappedFixedValue condition,
|
||||
except that no interpolation in time is supported. These should be
|
||||
located in the directory:
|
||||
|
||||
\verbatim
|
||||
\$FOAM_CASE/constant/boundaryData/\<patchName\>/points
|
||||
\$FOAM_CASE/constant/boundaryData/\<patchName\>/0/\{R|U|L\}
|
||||
Expression for the average length scale (tag:SST):
|
||||
Shur, M., Strelets, M., Travin, A.,
|
||||
Probst, A., Probst, S., Schwamborn, D., ... & Revell, A. (2018).
|
||||
Improved embedded approaches.
|
||||
In: Mockett C., Haase W., Schwamborn D. (eds)
|
||||
Go4Hybrid: Grey area mitigation for hybrid RANS-LES methods.
|
||||
Notes on Numerical Fluid Mechanics and Multidisciplinary Design.
|
||||
p. 51-87. Springer, Cham.
|
||||
DOI:10.1007/978-3-319-52995-0_3
|
||||
\endverbatim
|
||||
|
||||
Usage
|
||||
Example of the boundary condition specification:
|
||||
\verbatim
|
||||
<patchName>
|
||||
{
|
||||
// Mandatory entries
|
||||
type turbulentDFSEMInlet;
|
||||
delta <scalar>;
|
||||
R <PatchFunction1>;
|
||||
U <PatchFunction1>;
|
||||
L <PatchFunction1>;
|
||||
|
||||
// e.g.
|
||||
// R uniform (<Rxx> <Rxy> <Rxz> <Ryy> <Ryz> <Rzz>);
|
||||
// U uniform (<Ux> <Uy> <Uz>);
|
||||
// L uniform <L>;
|
||||
|
||||
// Optional entries
|
||||
d <scalar>;
|
||||
nCellPerEddy <label>;
|
||||
kappa <scalar>;
|
||||
Uref <scalar>;
|
||||
Lref <scalar>;
|
||||
scale <scalar>;
|
||||
m <scalar>;
|
||||
writeEddies <bool>;
|
||||
|
||||
// Inherited entries
|
||||
...
|
||||
}
|
||||
\endverbatim
|
||||
|
||||
where the entries mean:
|
||||
\table
|
||||
Property | Description | Required | Default value
|
||||
value | Restart value | yes |
|
||||
delta | Local limiting length scale | yes |
|
||||
R | Reynolds stress field | no |
|
||||
U | Velocity field | no |
|
||||
L | Turbulence length scale field | no |
|
||||
d | Eddy density (fill fraction) | no | 1
|
||||
kappa | Von Karman constant | no | 0.41
|
||||
mapMethod | Method to map reference values | no | nearestCell
|
||||
perturb | Point perturbation for interpolation | no | 1e-5
|
||||
interpolateR | Flag to interpolate the R field | no | false
|
||||
interpolateL | Flag to interpolate the L field | no | false
|
||||
interpolateU | Flag to interpolate the U field | no | false
|
||||
writeEddies | Flag to write eddies as OBJ file | no | no
|
||||
Property | Description | Type | Reqd | Deflt
|
||||
type | Type name: turbulentDFSEMInlet | word | yes | -
|
||||
delta | Characteristic length scale | scalar | yes | -
|
||||
R | Reynolds-stress tensor field <!--
|
||||
--> | PatchFunction1\<symmTensor\> | yes | -
|
||||
U | Mean velocity field <!--
|
||||
--> | PatchFunction1<vector> | yes | -
|
||||
L | Integral-length scale field <!--
|
||||
--> | PatchFunction1<scalar> | yes | -
|
||||
d | Ratio of sum of eddy volumes to eddy box volume <!--
|
||||
--> i.e. eddy density (fill fraction) | scalar | no | 1.0
|
||||
nCellPerEddy | Minimum eddy length in units of number of cells <!--
|
||||
--> | label | no | 5
|
||||
kappa | von Karman constant | scalar | no | 0.41
|
||||
Uref | Normalisation factor for Reynolds-stress <!--
|
||||
--> tensor and mean velocity | scalar | no | 1.0
|
||||
Lref | Normalisation factor for integral-length scale <!--
|
||||
--> | scalar | no | 1.0
|
||||
scale | Heuristic scaling factor being applied <!--
|
||||
--> on the normalisation factor C1 | scalar | no | 1.0
|
||||
m | The power of V defined in C1 | scalar | no | 0.5
|
||||
writeEddies | Flag to write eddies as OBJ file | bool | no | false
|
||||
\endtable
|
||||
|
||||
Note
|
||||
- The \c delta value typically represents the characteristic scale of flow
|
||||
or flow domain, e.g. a channel half-height
|
||||
- For \c R, \c U and \c L specification: if the entry is not user input,
|
||||
it is assumed that the data will be mapped
|
||||
The inherited entries are elaborated in:
|
||||
- \link fixedValueFvPatchFields.H \endlink
|
||||
- \link PatchFunction1.H \endlink
|
||||
- \link MappedFile.H \endlink
|
||||
|
||||
SeeAlso
|
||||
timeVaryingMappedFixedValueFvPatchField
|
||||
turbulentDigitalFilterInlet
|
||||
Note
|
||||
- The \c delta value typically represents the characteristic scale of flow
|
||||
or flow domain, e.g. a channel half height for plane channel flows.
|
||||
- \c nCellPerEddy and \c scale entries are heuristic entries
|
||||
which do not exist in the standard method, yet are necessary
|
||||
to reproduce the results published in the original journal paper.
|
||||
- In the original journal paper, \c C1 in Eq. 11 is not dimensionless.
|
||||
It is not clear whether this dimensionality issue was intentional.
|
||||
To alleviate this matter, users can alter the input entry \c m, which is
|
||||
the power of the eddy-box volume defined in the \c C1, to obtain a
|
||||
dimensionless \c C1 coefficient. The default value of \c m is 0.5,
|
||||
which is the value stated in the original journal paper,
|
||||
and \c m=1/3 leads to a dimensionless \c C1.
|
||||
|
||||
SourceFiles
|
||||
turbulentDFSEMInletFvPatchVectorField.C
|
||||
@ -94,15 +145,13 @@ SourceFiles
|
||||
#include "Random.H"
|
||||
#include "eddy.H"
|
||||
#include "pointIndexHit.H"
|
||||
#include "instantList.H"
|
||||
#include "PatchFunction1.H"
|
||||
|
||||
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
|
||||
|
||||
namespace Foam
|
||||
{
|
||||
|
||||
class pointToPointPlanarInterpolation;
|
||||
|
||||
/*---------------------------------------------------------------------------*\
|
||||
Class turbulentDFSEMInletFvPatchVectorField Declaration
|
||||
\*---------------------------------------------------------------------------*/
|
||||
@ -116,50 +165,38 @@ class turbulentDFSEMInletFvPatchVectorField
|
||||
//- Maximum number of attempts when seeding eddies
|
||||
static label seedIterMax_;
|
||||
|
||||
//- Characteristic length scale, e.g. half channel height
|
||||
//- Mean velocity field
|
||||
autoPtr<PatchFunction1<vector>> U_;
|
||||
|
||||
//- Reynolds stress tensor field
|
||||
autoPtr<PatchFunction1<symmTensor>> R_;
|
||||
|
||||
//- Integral-length scale field
|
||||
autoPtr<PatchFunction1<scalar>> L_;
|
||||
|
||||
//- Characteristic length scale
|
||||
const scalar delta_;
|
||||
|
||||
//- Ratio of sum of eddy volumes to eddy box volume; default = 1
|
||||
//- Ratio of sum of eddy volumes to eddy box volume, i.e. eddy density
|
||||
const scalar d_;
|
||||
|
||||
//- Von Karman constant
|
||||
//- von Karman constant
|
||||
const scalar kappa_;
|
||||
|
||||
//- Global numbering for faces
|
||||
mutable autoPtr<globalIndex> globalFacesPtr_;
|
||||
//- Normalisation factor for Reynolds-stress tensor and mean velocity
|
||||
const scalar Uref_;
|
||||
|
||||
//- Normalisation factor for integral-length scale
|
||||
const scalar Lref_;
|
||||
|
||||
// Table reading for patch inlet flow properties
|
||||
//- Heuristic scaling factor being applied on the normalisation factor
|
||||
const scalar scale_;
|
||||
|
||||
//- Fraction of perturbation (fraction of bounding box) to add
|
||||
scalar perturb_;
|
||||
//- The power of V defined in C1
|
||||
const scalar m_;
|
||||
|
||||
//- Interpolation scheme to use (nearestCell | planarInterpolation)
|
||||
word mapMethod_;
|
||||
|
||||
//- 2D interpolation (for 'planarInterpolation' mapMethod)
|
||||
mutable autoPtr<pointToPointPlanarInterpolation> mapperPtr_;
|
||||
|
||||
//- Flag to identify to interpolate the R field
|
||||
bool interpolateR_;
|
||||
|
||||
//- Flag to identify to interpolate the L field
|
||||
bool interpolateL_;
|
||||
|
||||
//- Flag to identify to interpolate the U field
|
||||
bool interpolateU_;
|
||||
|
||||
//- Reynolds stress tensor
|
||||
symmTensorField R_;
|
||||
|
||||
//- Length scale
|
||||
scalarField L_;
|
||||
|
||||
//- Inlet velocity
|
||||
vectorField U_;
|
||||
|
||||
//- Mean inlet velocity
|
||||
vector UMean_;
|
||||
//- Minimum eddy length in units of number of cells
|
||||
const label nCellPerEddy_;
|
||||
|
||||
|
||||
// Patch information
|
||||
@ -179,46 +216,51 @@ class turbulentDFSEMInletFvPatchVectorField
|
||||
//- Cumulative area fractions per processor
|
||||
scalarList sumTriMagSf_;
|
||||
|
||||
//- Patch normal into the domain
|
||||
vector patchNormal_;
|
||||
|
||||
//- List of eddies
|
||||
List<eddy> eddies_;
|
||||
//- Patch bounds (local processor)
|
||||
boundBox patchBounds_;
|
||||
|
||||
//- Minimum number of cells required to resolve an eddy
|
||||
label nCellPerEddy_;
|
||||
|
||||
//- Patch normal into the domain
|
||||
vector patchNormal_;
|
||||
// Eddy information
|
||||
|
||||
//- Eddy box volume
|
||||
scalar v0_;
|
||||
//- List of eddies
|
||||
List<eddy> eddies_;
|
||||
|
||||
//- Random number generator
|
||||
Random rndGen_;
|
||||
//- Eddy box volume
|
||||
scalar v0_;
|
||||
|
||||
//- Length scale per patch face
|
||||
scalarField sigmax_;
|
||||
//- Random number generator
|
||||
Random rndGen_;
|
||||
|
||||
//- Maximum length scale (across all processors)
|
||||
scalar maxSigmaX_;
|
||||
//- Integral-length scale per patch face
|
||||
scalarField sigmax_;
|
||||
|
||||
//- Global number of eddies
|
||||
label nEddy_;
|
||||
//- Maximum integral-length scale (across all processors)
|
||||
scalar maxSigmaX_;
|
||||
|
||||
//- Current time index (used for updating)
|
||||
label curTimeIndex_;
|
||||
//- Global number of eddies
|
||||
label nEddy_;
|
||||
|
||||
//- Patch bounds (local processor)
|
||||
boundBox patchBounds_;
|
||||
//- Current time index (used for updating)
|
||||
label curTimeIndex_;
|
||||
|
||||
//- Single processor contains all eddies (flag)
|
||||
bool singleProc_;
|
||||
//- Single processor contains all eddies (flag)
|
||||
bool singleProc_;
|
||||
|
||||
//- Flag to write the eddies to file
|
||||
bool writeEddies_;
|
||||
//- Flag to write the eddies to file
|
||||
bool writeEddies_;
|
||||
|
||||
|
||||
// Private Member Functions
|
||||
|
||||
//- Write Lumley coefficients to file
|
||||
void writeLumleyCoeffs() const;
|
||||
|
||||
//- Write eddy info in OBJ format
|
||||
void writeEddyOBJ() const;
|
||||
|
||||
//- Initialise info for patch point search
|
||||
void initialisePatch();
|
||||
|
||||
@ -231,37 +273,11 @@ class turbulentDFSEMInletFvPatchVectorField
|
||||
//- Initialise eddies
|
||||
void initialiseEddies();
|
||||
|
||||
//- Convect the eddies
|
||||
void convectEddies(const scalar deltaT);
|
||||
//- Convect the eddies with the bulk velocity
|
||||
void convectEddies(const vector& UBulk, const scalar deltaT);
|
||||
|
||||
//- Calculate the velocity fluctuation at a point
|
||||
vector uDashEddy(const List<eddy>& eddies, const point& globalX) const;
|
||||
|
||||
//- Helper function to interpolate values from the boundary data or
|
||||
//- read from dictionary
|
||||
template<class Type>
|
||||
tmp<Field<Type>> interpolateOrRead
|
||||
(
|
||||
const word& fieldName,
|
||||
const dictionary& dict,
|
||||
bool& interpolateField
|
||||
) const;
|
||||
|
||||
//- Helper function to interpolate values from the boundary data
|
||||
template<class Type>
|
||||
tmp<Field<Type>> interpolateBoundaryData
|
||||
(
|
||||
const word& fieldName
|
||||
) const;
|
||||
|
||||
//- Write Lumley coefficients to file
|
||||
void writeLumleyCoeffs() const;
|
||||
|
||||
//- Write eddy info in OBJ format
|
||||
void writeEddyOBJ() const;
|
||||
|
||||
//- Return a reference to the patch mapper object
|
||||
const pointToPointPlanarInterpolation& patchMapper() const;
|
||||
//- Return velocity fluctuation vector at a given point
|
||||
vector uPrimeEddy(const List<eddy>& eddies, const point& globalX) const;
|
||||
|
||||
//- Return eddies from remote processors that interact with local
|
||||
//- processor
|
||||
@ -345,11 +361,11 @@ public:
|
||||
|
||||
// Member Functions
|
||||
|
||||
//- Helper function to check that Reynold stresses are valid
|
||||
//- Return true if input Reynold stresses are valid
|
||||
static bool checkStresses(const symmTensorField& Rf);
|
||||
|
||||
|
||||
// Mapping functions
|
||||
// Mapping
|
||||
|
||||
//- Map (and resize as needed) from self given a mapping object
|
||||
virtual void autoMap(const fvPatchFieldMapper& m);
|
||||
@ -362,14 +378,16 @@ public:
|
||||
);
|
||||
|
||||
|
||||
// Evaluation functions
|
||||
// Evaluation
|
||||
|
||||
//- Update the coefficients associated with the patch field
|
||||
virtual void updateCoeffs();
|
||||
|
||||
|
||||
//- Write
|
||||
virtual void write(Ostream&) const;
|
||||
// IO
|
||||
|
||||
//- Write
|
||||
virtual void write(Ostream&) const;
|
||||
};
|
||||
|
||||
|
||||
@ -379,12 +397,6 @@ public:
|
||||
|
||||
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
|
||||
|
||||
#ifdef NoRepository
|
||||
#include "turbulentDFSEMInletFvPatchVectorFieldTemplates.C"
|
||||
#endif
|
||||
|
||||
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
|
||||
|
||||
#endif
|
||||
|
||||
// ************************************************************************* //
|
||||
|
||||
@ -1,109 +0,0 @@
|
||||
/*---------------------------------------------------------------------------*\
|
||||
========= |
|
||||
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
|
||||
\\ / O peration |
|
||||
\\ / A nd | www.openfoam.com
|
||||
\\/ M anipulation |
|
||||
-------------------------------------------------------------------------------
|
||||
Copyright (C) 2015 OpenFOAM Foundation
|
||||
Copyright (C) 2016-2020 OpenCFD Ltd
|
||||
-------------------------------------------------------------------------------
|
||||
License
|
||||
This file is part of OpenFOAM.
|
||||
|
||||
OpenFOAM is free software: you can redistribute it and/or modify it
|
||||
under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation, either version 3 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
|
||||
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
\*---------------------------------------------------------------------------*/
|
||||
|
||||
#include "pointToPointPlanarInterpolation.H"
|
||||
#include "Time.H"
|
||||
#include "rawIOField.H"
|
||||
|
||||
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
|
||||
|
||||
template<class Type>
|
||||
Foam::tmp<Foam::Field<Type>>
|
||||
Foam::turbulentDFSEMInletFvPatchVectorField::interpolateOrRead
|
||||
(
|
||||
const word& fieldName,
|
||||
const dictionary& dict,
|
||||
bool& interpolateField
|
||||
) const
|
||||
{
|
||||
if (dict.found(fieldName))
|
||||
{
|
||||
tmp<Field<Type>> tFld
|
||||
(
|
||||
new Field<Type>
|
||||
(
|
||||
fieldName,
|
||||
dict,
|
||||
this->patch().size()
|
||||
)
|
||||
);
|
||||
|
||||
interpolateField = false;
|
||||
return tFld;
|
||||
}
|
||||
else
|
||||
{
|
||||
interpolateField = true;
|
||||
return interpolateBoundaryData<Type>(fieldName);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template<class Type>
|
||||
Foam::tmp<Foam::Field<Type>>
|
||||
Foam::turbulentDFSEMInletFvPatchVectorField::interpolateBoundaryData
|
||||
(
|
||||
const word& fieldName
|
||||
) const
|
||||
{
|
||||
const word& patchName = this->patch().name();
|
||||
|
||||
const fileName valsFile
|
||||
(
|
||||
fileName
|
||||
(
|
||||
this->db().time().globalPath()
|
||||
/this->db().time().constant()
|
||||
/"boundaryData"
|
||||
/patchName
|
||||
/"0"
|
||||
/fieldName
|
||||
)
|
||||
);
|
||||
|
||||
IOobject io
|
||||
(
|
||||
valsFile, // absolute path
|
||||
this->db().time(),
|
||||
IOobject::MUST_READ,
|
||||
IOobject::NO_WRITE,
|
||||
false, // no need to register
|
||||
true // is global object (currently not used)
|
||||
);
|
||||
|
||||
const rawIOField<Type> vals(io, false);
|
||||
|
||||
Info<< "Turbulent DFSEM patch " << patchName
|
||||
<< ": interpolating field " << fieldName
|
||||
<< " from " << valsFile << endl;
|
||||
|
||||
return patchMapper().interpolate(vals);
|
||||
}
|
||||
|
||||
|
||||
// ************************************************************************* //
|
||||
Reference in New Issue
Block a user