47 "Synthetic Eddy Turbulence Method");
51 const std::weak_ptr<EquationSystem> &pEquation)
67 [[maybe_unused]]
const unsigned int &pNumForcingFields,
68 [[maybe_unused]]
const TiXmlElement *pForce)
71 m_spacedim = pFields[0]->GetGraph()->GetMeshDimension();
76 "Sythetic eddy method "
77 "only supports fully three-dimensional simulations");
83 const TiXmlElement *elmtInfTurb;
86 elmtInfTurb = pForce->FirstChildElement(
"ReynoldsStresses");
87 ASSERTL0(elmtInfTurb,
"Requires ReynoldsStresses tag specifying function "
88 "name which prescribes the reynodls stresses.");
90 std::string reyStressesFuncName = elmtInfTurb->GetText();
92 "Function '" + reyStressesFuncName +
93 "' is not defined in the session.");
96 std::vector<std::string> reyStressesVars = {
"r00",
"r10",
"r20",
99 for (
size_t i = 0; i < reyStressesVars.size(); ++i)
101 std::string varStr = reyStressesVars[i];
102 if (
m_session->DefinesFunction(reyStressesFuncName, varStr))
104 m_R[i] =
m_session->GetFunction(reyStressesFuncName, varStr);
109 "Missing parameter '" + varStr +
110 "' in the FUNCTION NAME = " + reyStressesFuncName +
116 elmtInfTurb = pForce->FirstChildElement(
"CharLengthScales");
117 ASSERTL0(elmtInfTurb,
"Requires CharLengthScales tag specifying function "
118 "name which prescribes the characteristic "
121 std::string charLenScalesFuncName = elmtInfTurb->GetText();
123 "Function '" + charLenScalesFuncName +
124 "' is not defined in the session.");
128 std::vector<std::string> lenScalesVars = {
"l00",
"l10",
"l20",
"l01",
"l11",
129 "l21",
"l02",
"l12",
"l22"};
133 for (
size_t i = 0; i < lenScalesVars.size(); ++i)
135 std::string varStr = lenScalesVars[i];
136 if (
m_session->DefinesFunction(charLenScalesFuncName, varStr))
138 clsAux =
m_session->GetFunction(charLenScalesFuncName, varStr);
144 "Missing parameter '" + varStr +
145 "' in the FUNCTION NAME = " + charLenScalesFuncName +
154 elmtInfTurb = pForce->FirstChildElement(
"BoxOfEddies");
156 "Unable to find BoxOfEddies tag. in SyntheticTurbulence forcing");
160 std::stringstream boxStream;
161 std::string boxStr = elmtInfTurb->GetText();
162 boxStream.str(boxStr);
164 for (
size_t i = 0; i < (2 *
m_spacedim - 1); ++i)
169 m_rc[i] = boost::lexical_cast<NekDouble>(boxStr);
180 "Missing parameter in the BoxOfEddies tag");
185 elmtInfTurb = pForce->FirstChildElement(
"Sigma");
187 "Unable to find Sigma tag. in SyntheticTurbulence forcing");
188 std::string sigmaStr = elmtInfTurb->GetText();
189 m_sigma = boost::lexical_cast<NekDouble>(sigmaStr);
192 elmtInfTurb = pForce->FirstChildElement(
"BulkVelocity");
194 "Unable to find BulkVelocity tag. in SyntheticTurbulence forcing");
195 std::string bVelStr = elmtInfTurb->GetText();
196 m_Ub = boost::lexical_cast<NekDouble>(bVelStr);
199 elmtInfTurb = pForce->FirstChildElement(
"TestCase");
200 const char *tcaseStr = (elmtInfTurb) ? elmtInfTurb->GetText() :
"NoName";
201 m_tCase = (strcmp(tcaseStr,
"ChanFlow3D") == 0) ?
true :
false;
228 srand(time(
nullptr));
232 for (
int i = 0; i < pFields.size(); ++i)
238 for (
size_t n = 0; n <
m_N; ++n)
290 int nqTot = pFields[0]->GetTotPoints();
297 for (
size_t i = 0; i < nqTot; ++i)
304 convTurbLength =
m_l[3 * k];
306 convTurbTime[k][i] = convTurbLength /
m_Ub;
326 int nqTot = pFields[0]->GetTotPoints();
328 int nElmts = pFields[0]->GetNumElmts();
343 for (
size_t e = 0; e < nElmts; ++e)
345 nqe = pFields[0]->GetExp(e)->GetTotPoints();
351 pFields[0]->GetExp(e)->GetCoords(coords0, coords1, coords2);
353 for (
size_t i = 0; i < nqe; ++i)
360 smoothFac[0][count + i] =
361 exp((-0.5 * M_PI * mod) /
362 (convTurbTime[0][count + i] *
363 convTurbTime[0][count + i] *
m_Ub *
m_Ub));
364 smoothFac[1][count + i] =
365 exp((-0.5 * M_PI * mod) /
366 (convTurbTime[1][count + i] *
367 convTurbTime[1][count + i] *
m_Ub *
m_Ub));
368 smoothFac[2][count + i] =
369 exp((-0.5 * M_PI * mod) /
370 (convTurbTime[2][count + i] *
371 convTurbTime[2][count + i] *
m_Ub *
m_Ub));
393 int nqTot = pFields[0]->GetTotPoints();
404 for (
size_t j = 0; j < k + 1; ++j)
406 for (
size_t i = 0; i < nqTot; ++i)
411 velFluc[n][k * nqTot + i] +=
413 stochasticSignal[n][j * nqTot + i];
434 int nqTot = pFields[0]->GetTotPoints();
436 int nElmts = pFields[0]->GetNumElmts();
458 for (
size_t e = 0; e < nElmts; ++e)
460 nqe = pFields[0]->GetExp(e)->GetTotPoints();
466 pFields[0]->GetExp(e)->GetCoords(coords0, coords1, coords2);
469 for (
size_t i = 0; i < nqe; ++i)
473 stochasticSignal[n][j * nqTot + nqeCount + i] =
494 return stochasticSignal;
504 for (
size_t n = 0; n <
m_N; ++n)
546 int nqTot = pFields[0]->GetTotPoints();
548 int nVars = pFields.size();
552 for (
size_t j = 0; j < nVars; ++j)
554 for (
size_t i = 0; i < nqTot; ++i)
569 for (
size_t n = 0; n <
m_N; ++n)
596 if (
abs(coord) <= (xiMaxVal + epsilon))
598 return ((1.0 / (
m_sigma *
sqrt(2.0 * M_PI * constC))) *
632 return (0.5 * 0.5 * step * sum);
663 epsilonSign[j][n] = 1;
682 int nqTot = pFields[0]->GetTotPoints();
684 int nElmts = pFields[0]->GetNumElmts();
692 for (
size_t e = 0; e < nElmts; ++e)
694 nqe = pFields[0]->GetExp(e)->GetTotPoints();
700 pFields[0]->GetExp(e)->GetCoords(coords0, coords1, coords2);
702 for (
size_t i = 0; i < nqe; ++i)
721 int nqTot = pFields[0]->GetTotPoints();
723 int nVars = pFields.size();
726 for (
size_t i = 0; i <
m_N; ++i)
729 for (
size_t j = 0; j < nVars; ++j)
732 for (
size_t k = 0; k < nqTot; ++k)
754 (coord1 >= (
m_rc[1] - 0.5 *
m_lyz[0] - tol)) &&
755 (coord1 <= (
m_rc[1] + 0.5 *
m_lyz[0] + tol)) &&
756 (coord2 >= (
m_rc[2] - 0.5 *
m_lyz[1] - tol)) &&
757 (coord2 <= (
m_rc[2] + 0.5 *
m_lyz[1] + tol)))
825 int nqTot = pFields[0]->GetTotPoints();
829 int nElmts = pFields[0]->GetNumElmts();
837 for (
size_t e = 0; e < nElmts; ++e)
839 nqe = pFields[0]->GetExp(e)->GetTotPoints();
846 pFields[0]->GetExp(e)->GetCoords(coords0, coords1, coords2);
849 for (
size_t i = 0; i < nqe; ++i)
859 A[l] =
m_R[l]->Evaluate(coords0[i], coords1[i], coords2[i]);
866 std::string message =
867 "ERROR: The " + std::to_string(-info) +
868 "th parameter had an illegal parameter for dpptrf";
872 for (
size_t l = 0; l < diagSize; ++l)
#define ASSERTL0(condition, msg)
#define NEKERROR(type, msg)
Assert Level 0 – Fundamental assert which is used whether in FULLDEBUG, DEBUG or OPT compilation mode...
tKey RegisterCreatorFunction(tKey idKey, CreatorFunction classCreator, std::string pDesc="")
Register a class with the factory.
Defines a forcing term to be explicitly applied.
Array< OneD, Array< OneD, NekDouble > > m_Forcing
Evaluated forcing function.
LibUtilities::SessionReaderSharedPtr m_session
Session reader.
SOLVER_UTILS_EXPORT void SetBoxOfEddiesMask(const Array< OneD, MultiRegions::ExpListSharedPtr > &pFields)
Set box of eddies mask.
NekDouble m_Ub
Bulk velocity.
std::map< int, LibUtilities::EquationSharedPtr > m_R
Array< OneD, NekDouble > m_lyz
Inlet length in the y-direction and z-direction.
Array< OneD, NekDouble > m_lref
Reference lenghts.
SOLVER_UTILS_EXPORT Array< OneD, Array< OneD, NekDouble > > ComputeSmoothingFactor(const Array< OneD, MultiRegions::ExpListSharedPtr > &pFields, Array< OneD, Array< OneD, NekDouble > > convTurb)
Compute Smoothing Factor.
SOLVER_UTILS_EXPORT void v_ApplyCoeff(const Array< OneD, MultiRegions::ExpListSharedPtr > &pFields, const Array< OneD, Array< OneD, NekDouble > > &inarray, Array< OneD, Array< OneD, NekDouble > > &outarray, const NekDouble &time) override
Apply forcing term if an eddy left the box of eddies and update the eddies positions.
Array< OneD, Array< OneD, Array< OneD, NekDouble > > > m_ForcingEddy
Forcing for each eddy.
SOLVER_UTILS_EXPORT ForcingSyntheticEddy(const LibUtilities::SessionReaderSharedPtr &pSession, const std::weak_ptr< EquationSystem > &pEquation)
int m_N
Number of eddies in the box.
SOLVER_UTILS_EXPORT NekDouble ComputeConstantC(int row, int col)
Compute Constant C.
int m_spacedim
Space dimension.
Array< OneD, NekDouble > m_l
Characteristic lenght scales.
bool m_tCase
Check for test case.
static SOLVER_UTILS_EXPORT std::string className
Name of the class.
SOLVER_UTILS_EXPORT Array< OneD, Array< OneD, NekDouble > > ComputeStochasticSignal(const Array< OneD, MultiRegions::ExpListSharedPtr > &pFields)
Compute Stochastic Signal.
SOLVER_UTILS_EXPORT Array< OneD, Array< OneD, int > > GenerateRandomOneOrMinusOne()
Compute Random 1 or -1 value.
SOLVER_UTILS_EXPORT Array< OneD, Array< OneD, NekDouble > > ComputeVelocityFluctuation(const Array< OneD, MultiRegions::ExpListSharedPtr > &pFields, Array< OneD, Array< OneD, NekDouble > > stochasticSignal)
Compute Velocity Fluctuation.
SOLVER_UTILS_EXPORT void UpdateEddiesPositions()
Update positions of the eddies inside the box.
SOLVER_UTILS_EXPORT NekDouble ComputeGaussian(NekDouble coord, NekDouble xiMaxVal, NekDouble constC=1.0)
Compute Gaussian.
std::vector< unsigned int > m_eddiesIDForcing
Eddies that add to the domain.
SOLVER_UTILS_EXPORT void SetNumberOfEddies()
Set the Number of the Eddies in the box.
SOLVER_UTILS_EXPORT void InitialiseForcingEddy(const Array< OneD, MultiRegions::ExpListSharedPtr > &pFields)
Initialise forcing term for each eddy.
Array< OneD, NekDouble > m_rc
Center of the inlet plane.
SOLVER_UTILS_EXPORT void v_Apply(const Array< OneD, MultiRegions::ExpListSharedPtr > &pFields, const Array< OneD, Array< OneD, NekDouble > > &inarray, Array< OneD, Array< OneD, NekDouble > > &outarray, const NekDouble &time) override
Apply forcing term if an eddy left the box of eddies and update the eddies positions.
SOLVER_UTILS_EXPORT void ComputeInitialLocationTestCase()
Compute the initial location of the eddies for the test case.
bool m_calcForcing
Check when the forcing should be applied.
SOLVER_UTILS_EXPORT void v_InitObject(const Array< OneD, MultiRegions::ExpListSharedPtr > &pFields, const unsigned int &pNumForcingFields, const TiXmlElement *pForce) override
Read input from xml file and initialise the class members. The main parameters are the characteristic...
static SOLVER_UTILS_EXPORT ForcingSharedPtr create(const LibUtilities::SessionReaderSharedPtr &pSession, const std::weak_ptr< EquationSystem > &pEquation, const Array< OneD, MultiRegions::ExpListSharedPtr > &pFields, const unsigned int &pNumForcingFields, const TiXmlElement *pForce)
Creates an instance of this class.
NekDouble m_sigma
Standard deviation.
SOLVER_UTILS_EXPORT void ComputeInitialRandomLocationOfEddies()
Compute the initial position of the eddies inside the box.
SOLVER_UTILS_EXPORT void ComputeXiMax()
Set Xi max.
Array< OneD, NekDouble > m_xiMax
Xi max.
SOLVER_UTILS_EXPORT void RemoveEddiesFromForcing(const Array< OneD, MultiRegions::ExpListSharedPtr > &pFields)
Remove eddy from forcing term.
Array< OneD, Array< OneD, NekDouble > > m_Cholesky
Cholesky decomposition of the Reynolds Stresses for all points in the mesh.
SOLVER_UTILS_EXPORT Array< OneD, Array< OneD, NekDouble > > ComputeCharConvTurbTime(const Array< OneD, MultiRegions::ExpListSharedPtr > &pFields)
Compute Characteristic Convective Turbulent Time.
SOLVER_UTILS_EXPORT void ComputeRefLenghts()
Set reference lengths.
Array< OneD, int > m_mask
Box of eddies mask.
SOLVER_UTILS_EXPORT bool InsideBoxOfEddies(NekDouble coord0, NekDouble coord1, NekDouble coord2)
Check if point is inside the box of eddies.
SOLVER_UTILS_EXPORT void SetCholeskyReyStresses(const Array< OneD, MultiRegions::ExpListSharedPtr > &pFields)
Calculates the Cholesky decomposition of the Reynolds Stresses in each degree of freedom of the mesh.
Array< OneD, Array< OneD, NekDouble > > m_eddyPos
Eddy position.
NekDouble m_gamma
Ration of specific heats.
static void Dpptrf(const char &uplo, const int &n, double *ap, int &info)
Cholesky factor a real positive definite packed-symmetric matrix.
std::shared_ptr< SessionReader > SessionReaderSharedPtr
std::shared_ptr< Equation > EquationSharedPtr
ForcingFactory & GetForcingFactory()
Declaration of the forcing factory singleton.
scalarT< T > abs(scalarT< T > in)
scalarT< T > sqrt(scalarT< T > in)