Merge branch 'develop' into feature/fluidized_bed_chemistry_cases

tutorials/cfdemSolverRhoPimpleChem/PolydisperseFluidizedBed/R2_FB/DEM/in.liggghts_run
This commit is contained in:
danielque
2023-02-03 12:37:51 +01:00
75 changed files with 1044 additions and 21134 deletions

View File

@ -2,7 +2,7 @@
cd ${0%/*} || exit 1 # Run from this directory cd ${0%/*} || exit 1 # Run from this directory
set -x set -x
wclean libso multiphaseMixture wclean libso multiphaseMixtureScalar
wclean wclean
#------------------------------------------------------------------------------ #------------------------------------------------------------------------------

View File

@ -6,7 +6,7 @@ targetType=libso
. $WM_PROJECT_DIR/wmake/scripts/AllwmakeParseArguments . $WM_PROJECT_DIR/wmake/scripts/AllwmakeParseArguments
set -x set -x
wmake $targetType multiphaseMixture wmake $targetType multiphaseMixtureScalar
wmake wmake
#------------------------------------------------------------------------------ #------------------------------------------------------------------------------

View File

@ -6,7 +6,7 @@ include $(CFDEM_ADD_LIBS_DIR)/additionalLibs
EXE_INC = \ EXE_INC = \
$(PFLAGS) \ $(PFLAGS) \
-I$(CFDEM_OFVERSION_DIR) \ -I$(CFDEM_OFVERSION_DIR) \
-ImultiphaseMixture/lnInclude \ -ImultiphaseMixtureScalar/lnInclude \
-I$(LIB_SRC)/transportModels \ -I$(LIB_SRC)/transportModels \
-I$(LIB_SRC)/transportModels/incompressible/lnInclude \ -I$(LIB_SRC)/transportModels/incompressible/lnInclude \
-I$(LIB_SRC)/transportModels/interfaceProperties/lnInclude \ -I$(LIB_SRC)/transportModels/interfaceProperties/lnInclude \

View File

@ -30,7 +30,7 @@ Description
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
#include "fvCFD.H" #include "fvCFD.H"
#include "multiphaseMixture.H" #include "multiphaseMixtureScalar.H"
#include "turbulentTransportModel.H" #include "turbulentTransportModel.H"
#include "pimpleControl.H" #include "pimpleControl.H"
#include "fvOptions.H" #include "fvOptions.H"

View File

@ -88,7 +88,7 @@ surfaceScalarField phi
linearInterpolate(U*voidfraction) & mesh.Sf() linearInterpolate(U*voidfraction) & mesh.Sf()
); );
multiphaseMixture mixture(U, phi, voidfraction); multiphaseMixtureScalar mixture(U, phi, voidfraction);
// Need to store rho for ddt(rho, U) // Need to store rho for ddt(rho, U)
volScalarField rho volScalarField rho

View File

@ -1,5 +1,5 @@
phase/phase.C phase/phase.C
alphaContactAngle/alphaContactAngleFvPatchScalarField.C alphaContactAngle/alphaContactAngleFvPatchScalarField.C
multiphaseMixture.C multiphaseMixtureScalar.C
LIB = $(CFDEM_LIB_DIR)/libcfdemMultiphaseInterFoamScalar LIB = $(CFDEM_LIB_DIR)/libcfdemMultiphaseInterFoamScalar

View File

@ -26,7 +26,7 @@ Class
Description Description
Contact-angle boundary condition for multi-phase interface-capturing Contact-angle boundary condition for multi-phase interface-capturing
simulations. Used in conjuction with multiphaseMixture. simulations. Used in conjuction with multiphaseMixtureScalar.
SourceFiles SourceFiles
alphaContactAngleFvPatchScalarField.C alphaContactAngleFvPatchScalarField.C
@ -37,7 +37,7 @@ SourceFiles
#define alphaContactAngleFvPatchScalarField_H #define alphaContactAngleFvPatchScalarField_H
#include "zeroGradientFvPatchFields.H" #include "zeroGradientFvPatchFields.H"
#include "multiphaseMixture.H" #include "multiphaseMixtureScalar.H"
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
@ -117,8 +117,8 @@ public:
typedef HashTable typedef HashTable
< <
interfaceThetaProps, interfaceThetaProps,
multiphaseMixture::interfacePair, multiphaseMixtureScalar::interfacePair,
multiphaseMixture::interfacePair::hash multiphaseMixtureScalar::interfacePair::hash
> thetaPropsTable; > thetaPropsTable;

View File

@ -18,7 +18,7 @@ License
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
#include "multiphaseMixture.H" #include "multiphaseMixtureScalar.H"
#include "alphaContactAngleFvPatchScalarField.H" #include "alphaContactAngleFvPatchScalarField.H"
#include "Time.H" #include "Time.H"
#include "subCycle.H" #include "subCycle.H"
@ -31,13 +31,13 @@ License
// * * * * * * * * * * * * * * * Static Member Data * * * * * * * * * * * * // // * * * * * * * * * * * * * * * Static Member Data * * * * * * * * * * * * //
const Foam::scalar Foam::multiphaseMixture::convertToRad = const Foam::scalar Foam::multiphaseMixtureScalar::convertToRad =
Foam::constant::mathematical::pi/180.0; Foam::constant::mathematical::pi/180.0;
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * // // * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
void Foam::multiphaseMixture::calcAlphas() void Foam::multiphaseMixtureScalar::calcAlphas()
{ {
scalar level = 0.0; scalar level = 0.0;
alphas_ == 0.0; alphas_ == 0.0;
@ -51,7 +51,7 @@ void Foam::multiphaseMixture::calcAlphas()
Foam::tmp<Foam::volScalarField> Foam::tmp<Foam::volScalarField>
Foam::multiphaseMixture::calcNu() const Foam::multiphaseMixtureScalar::calcNu() const
{ {
PtrDictionary<phase>::const_iterator iter = phases_.begin(); PtrDictionary<phase>::const_iterator iter = phases_.begin();
@ -74,7 +74,7 @@ Foam::multiphaseMixture::calcNu() const
} }
Foam::tmp<Foam::surfaceScalarField> Foam::tmp<Foam::surfaceScalarField>
Foam::multiphaseMixture::calcStf() const Foam::multiphaseMixtureScalar::calcStf() const
{ {
tmp<surfaceScalarField> tstf tmp<surfaceScalarField> tstf
( (
@ -134,7 +134,7 @@ Foam::multiphaseMixture::calcStf() const
// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
Foam::multiphaseMixture::multiphaseMixture Foam::multiphaseMixtureScalar::multiphaseMixtureScalar
( (
const volVectorField& U, const volVectorField& U,
const surfaceScalarField& phi, const surfaceScalarField& phi,
@ -230,7 +230,7 @@ Foam::multiphaseMixture::multiphaseMixture
// * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * * //
Foam::tmp<Foam::volScalarField> Foam::tmp<Foam::volScalarField>
Foam::multiphaseMixture::rho() const Foam::multiphaseMixtureScalar::rho() const
{ {
PtrDictionary<phase>::const_iterator iter = phases_.begin(); PtrDictionary<phase>::const_iterator iter = phases_.begin();
@ -247,7 +247,7 @@ Foam::multiphaseMixture::rho() const
Foam::tmp<Foam::scalarField> Foam::tmp<Foam::scalarField>
Foam::multiphaseMixture::rho(const label patchi) const Foam::multiphaseMixtureScalar::rho(const label patchi) const
{ {
PtrDictionary<phase>::const_iterator iter = phases_.begin(); PtrDictionary<phase>::const_iterator iter = phases_.begin();
@ -264,9 +264,9 @@ Foam::multiphaseMixture::rho(const label patchi) const
Foam::tmp<Foam::volScalarField> Foam::tmp<Foam::volScalarField>
Foam::multiphaseMixture::mu() const Foam::multiphaseMixtureScalar::mu() const
{ {
Info << "In multiphasemixture mu()" << endl; Info << "In multiphaseMixtureScalar mu()" << endl;
return rho()*nu(); return rho()*nu();
// PtrDictionary<phase>::const_iterator iter = phases_.begin(); // PtrDictionary<phase>::const_iterator iter = phases_.begin();
@ -283,7 +283,7 @@ Foam::multiphaseMixture::mu() const
Foam::tmp<Foam::scalarField> Foam::tmp<Foam::scalarField>
Foam::multiphaseMixture::mu(const label patchi) const Foam::multiphaseMixtureScalar::mu(const label patchi) const
{ {
PtrDictionary<phase>::const_iterator iter = phases_.begin(); PtrDictionary<phase>::const_iterator iter = phases_.begin();
@ -306,7 +306,7 @@ Foam::multiphaseMixture::mu(const label patchi) const
Foam::tmp<Foam::surfaceScalarField> Foam::tmp<Foam::surfaceScalarField>
Foam::multiphaseMixture::muf() const Foam::multiphaseMixtureScalar::muf() const
{ {
return nuf()*fvc::interpolate(rho()); return nuf()*fvc::interpolate(rho());
@ -327,13 +327,13 @@ Foam::multiphaseMixture::muf() const
Foam::tmp<Foam::volScalarField> Foam::tmp<Foam::volScalarField>
Foam::multiphaseMixture::nu() const Foam::multiphaseMixtureScalar::nu() const
{ {
return nu_; return nu_;
} }
Foam::tmp<Foam::scalarField> Foam::tmp<Foam::scalarField>
Foam::multiphaseMixture::nu(const label patchi) const Foam::multiphaseMixtureScalar::nu(const label patchi) const
{ {
//return nu_.boundaryField()[patchi]; //return nu_.boundaryField()[patchi];
PtrDictionary<phase>::const_iterator iter = phases_.begin(); PtrDictionary<phase>::const_iterator iter = phases_.begin();
@ -355,7 +355,7 @@ Foam::multiphaseMixture::nu(const label patchi) const
Foam::tmp<Foam::surfaceScalarField> Foam::tmp<Foam::surfaceScalarField>
Foam::multiphaseMixture::nuf() const Foam::multiphaseMixtureScalar::nuf() const
{ {
//return muf()/fvc::interpolate(rho()); //return muf()/fvc::interpolate(rho());
PtrDictionary<phase>::const_iterator iter = phases_.begin(); PtrDictionary<phase>::const_iterator iter = phases_.begin();
@ -374,7 +374,7 @@ Foam::multiphaseMixture::nuf() const
} }
Foam::tmp<Foam::volScalarField> Foam::tmp<Foam::volScalarField>
Foam::multiphaseMixture::Cp() const Foam::multiphaseMixtureScalar::Cp() const
{ {
PtrDictionary<phase>::const_iterator iter = phases_.begin(); PtrDictionary<phase>::const_iterator iter = phases_.begin();
@ -395,7 +395,7 @@ Foam::multiphaseMixture::Cp() const
} }
Foam::tmp<Foam::volScalarField> Foam::tmp<Foam::volScalarField>
Foam::multiphaseMixture::kf() const Foam::multiphaseMixtureScalar::kf() const
{ {
PtrDictionary<phase>::const_iterator iter = phases_.begin(); PtrDictionary<phase>::const_iterator iter = phases_.begin();
@ -417,7 +417,7 @@ Foam::multiphaseMixture::kf() const
} }
Foam::tmp<Foam::volScalarField> Foam::tmp<Foam::volScalarField>
Foam::multiphaseMixture::D() const Foam::multiphaseMixtureScalar::D() const
{ {
PtrDictionary<phase>::const_iterator iter = phases_.begin(); PtrDictionary<phase>::const_iterator iter = phases_.begin();
@ -439,7 +439,7 @@ Foam::multiphaseMixture::D() const
} }
Foam::tmp<Foam::volScalarField> Foam::tmp<Foam::volScalarField>
Foam::multiphaseMixture::Cs() const Foam::multiphaseMixtureScalar::Cs() const
{ {
PtrDictionary<phase>::const_iterator iter = phases_.begin(); PtrDictionary<phase>::const_iterator iter = phases_.begin();
@ -456,7 +456,7 @@ Foam::multiphaseMixture::Cs() const
} }
Foam::tmp<Foam::surfaceScalarField> Foam::tmp<Foam::surfaceScalarField>
Foam::multiphaseMixture::diffusionCorrection() const Foam::multiphaseMixtureScalar::diffusionCorrection() const
{ {
surfaceScalarField numerator surfaceScalarField numerator
@ -517,7 +517,7 @@ Foam::multiphaseMixture::diffusionCorrection() const
return correction; return correction;
} }
void Foam::multiphaseMixture::solve() void Foam::multiphaseMixtureScalar::solve()
{ {
correct(); correct();
@ -570,7 +570,7 @@ void Foam::multiphaseMixture::solve()
} }
void Foam::multiphaseMixture::correct() void Foam::multiphaseMixtureScalar::correct()
{ {
forAllIter(PtrDictionary<phase>, phases_, iter) forAllIter(PtrDictionary<phase>, phases_, iter)
{ {
@ -579,7 +579,7 @@ void Foam::multiphaseMixture::correct()
} }
Foam::tmp<Foam::surfaceVectorField> Foam::multiphaseMixture::nHatfv Foam::tmp<Foam::surfaceVectorField> Foam::multiphaseMixtureScalar::nHatfv
( (
const volScalarField& alpha1, const volScalarField& alpha1,
const volScalarField& alpha2 const volScalarField& alpha2
@ -605,7 +605,7 @@ Foam::tmp<Foam::surfaceVectorField> Foam::multiphaseMixture::nHatfv
} }
Foam::tmp<Foam::surfaceScalarField> Foam::multiphaseMixture::nHatf Foam::tmp<Foam::surfaceScalarField> Foam::multiphaseMixtureScalar::nHatf
( (
const volScalarField& alpha1, const volScalarField& alpha1,
const volScalarField& alpha2 const volScalarField& alpha2
@ -622,7 +622,7 @@ Foam::tmp<Foam::surfaceScalarField> Foam::multiphaseMixture::nHatf
// The dynamic contact angle is calculated from the component of the // The dynamic contact angle is calculated from the component of the
// velocity on the direction of the interface, parallel to the wall. // velocity on the direction of the interface, parallel to the wall.
void Foam::multiphaseMixture::correctContactAngle void Foam::multiphaseMixtureScalar::correctContactAngle
( (
const phase& alpha1, const phase& alpha1,
const phase& alpha2, const phase& alpha2,
@ -726,7 +726,7 @@ void Foam::multiphaseMixture::correctContactAngle
} }
Foam::tmp<Foam::volScalarField> Foam::multiphaseMixture::K Foam::tmp<Foam::volScalarField> Foam::multiphaseMixtureScalar::K
( (
const phase& alpha1, const phase& alpha1,
const phase& alpha2 const phase& alpha2
@ -742,7 +742,7 @@ Foam::tmp<Foam::volScalarField> Foam::multiphaseMixture::K
Foam::tmp<Foam::volScalarField> Foam::tmp<Foam::volScalarField>
Foam::multiphaseMixture::nearInterface() const Foam::multiphaseMixtureScalar::nearInterface() const
{ {
tmp<volScalarField> tnearInt tmp<volScalarField> tnearInt
( (
@ -768,7 +768,7 @@ Foam::multiphaseMixture::nearInterface() const
} }
void Foam::multiphaseMixture::solveAlphas void Foam::multiphaseMixtureScalar::solveAlphas
( (
const scalar cAlpha const scalar cAlpha
) )
@ -901,7 +901,7 @@ void Foam::multiphaseMixture::solveAlphas
} }
bool Foam::multiphaseMixture::read() bool Foam::multiphaseMixtureScalar::read()
{ {
if (transportModel::read()) if (transportModel::read())
{ {

View File

@ -17,10 +17,10 @@ License
Copyright (C) 2018- Mathias Vångö, JKU Linz, Austria Copyright (C) 2018- Mathias Vångö, JKU Linz, Austria
Class Class
multiphaseMixture multiphaseMixtureScalar
Description Description
This class is based on the OpenFOAM(R) Foam::multiphaseMixture class, This class is based on the OpenFOAM(R) Foam::multiphaseMixtureScalar class,
which is an incompressible multi-phase mixture with built in solution which is an incompressible multi-phase mixture with built in solution
for the phase fractions with interface compression for interface-capturing. for the phase fractions with interface compression for interface-capturing.
It has been extended to include the void fraction in the volume fraction It has been extended to include the void fraction in the volume fraction
@ -33,11 +33,11 @@ Description
between each phase-pair. between each phase-pair.
SourceFiles SourceFiles
multiphaseMixture.C multiphaseMixtureScalar.C
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
#ifndef multiphaseMixture_H #ifndef multiphaseMixtureScalar_H
#define multiphaseMixture_H #define multiphaseMixtureScalar_H
#include "incompressible/transportModel/transportModel.H" #include "incompressible/transportModel/transportModel.H"
#include "IOdictionary.H" #include "IOdictionary.H"
@ -52,10 +52,10 @@ namespace Foam
{ {
/*---------------------------------------------------------------------------*\ /*---------------------------------------------------------------------------*\
Class multiphaseMixture Declaration Class multiphaseMixtureScalar Declaration
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
class multiphaseMixture class multiphaseMixtureScalar
: :
public IOdictionary, public IOdictionary,
public transportModel public transportModel
@ -191,7 +191,7 @@ public:
// Constructors // Constructors
//- Construct from components //- Construct from components
multiphaseMixture multiphaseMixtureScalar
( (
const volVectorField& U, const volVectorField& U,
const surfaceScalarField& phi, const surfaceScalarField& phi,
@ -200,7 +200,7 @@ public:
//- Destructor //- Destructor
virtual ~multiphaseMixture() virtual ~multiphaseMixtureScalar()
{} {}

View File

@ -26,7 +26,7 @@ Class
Description Description
Single incompressible phase derived from the phase-fraction. Single incompressible phase derived from the phase-fraction.
Used as part of the multiPhaseMixture for interface-capturing multi-phase Used as part of the multiphaseMixtureScalar for interface-capturing multi-phase
simulations. simulations.
SourceFiles SourceFiles

View File

@ -12,7 +12,8 @@ EXE_INC = \
-I$(CFDEM_SRC_DIR)/lagrangian/cfdemParticle/lnInclude \ -I$(CFDEM_SRC_DIR)/lagrangian/cfdemParticle/lnInclude \
-I$(CFDEM_SRC_DIR)/lagrangian/cfdemParticle/cfdTools \ -I$(CFDEM_SRC_DIR)/lagrangian/cfdemParticle/cfdTools \
-I$(CFDEM_SRC_DIR)/lagrangian/cfdemParticle/derived/cfdemCloudRec \ -I$(CFDEM_SRC_DIR)/lagrangian/cfdemParticle/derived/cfdemCloudRec \
-I$(LIB_SRC)/sampling/lnInclude -I$(LIB_SRC)/sampling/lnInclude \
-Wno-deprecated-copy
EXE_LIBS = \ EXE_LIBS = \
-L$(CFDEM_LIB_DIR)\ -L$(CFDEM_LIB_DIR)\

View File

@ -51,8 +51,4 @@
thermo.correct(); thermo.correct();
Info<< "T max/min/ave : " << max(T).value() << " " << min(T).value() << " " << average(T).value() << endl; Info<< "T max/min/ave : " << max(T).value() << " " << min(T).value() << " " << average(T).value() << endl;
particleCloud.clockM().start(31,"energySolve");
particleCloud.solve();
particleCloud.clockM().stop("energySolve");
} }

View File

@ -55,8 +55,4 @@ fvScalarMatrix EEqn
Info << "Cpv :" << max(Cpv).value() << " " << min(Cpv).value() << endl; Info << "Cpv :" << max(Cpv).value() << " " << min(Cpv).value() << endl;
Info<< "T max/min : " << max(T).value() << " " << min(T).value() << endl; Info<< "T max/min : " << max(T).value() << " " << min(T).value() << endl;
Info << "he max/min : " << max(he).value() << " " << min(he).value() << endl; Info << "he max/min : " << max(he).value() << " " << min(he).value() << endl;
particleCloud.clockM().start(31,"energySolve");
particleCloud.solve();
particleCloud.clockM().stop("energySolve");
} }

View File

@ -303,18 +303,4 @@
mesh, mesh,
dimensionedScalar("zero",dimensionSet(0, -3, 0, 0, 1),0) dimensionedScalar("zero",dimensionSet(0, -3, 0, 0, 1),0)
); );
volScalarField dSauter
(
IOobject
(
"dSauter",
runTime.timeName(),
mesh,
IOobject::READ_IF_PRESENT,
IOobject::AUTO_WRITE
),
mesh,
dimensionedScalar("zero",dimensionSet(0, 1, 0, 0, 0,0,0),0)
);
//=============================== //===============================

View File

@ -1,4 +1,4 @@
volScalarField rhoeps = rhoRec*voidfractionRec; rhoeps = rhoRec*voidfractionRec;
particleCloud.energyContributions(Qsource); particleCloud.energyContributions(Qsource);
@ -23,10 +23,17 @@
fvOptions(rhoeps, T) // no fvOptions support yet fvOptions(rhoeps, T) // no fvOptions support yet
); );
fvOptions.constrain(TEqn); // no fvOptions support yet // fvOptions.constrain(TEqn); // no fvOptions support yet
TEqn.relax();
TEqn.solve(); TEqn.solve();
T = max(T, TMin);
T = min(T, TMax);
Info<< "T max/min/ave : " << max(T).value() << " " << min(T).value() << " " << average(T).value() << endl;
particleCloud.clockM().start(31,"postFlow"); particleCloud.clockM().start(31,"postFlow");
counter++; counter++;

View File

@ -73,6 +73,9 @@
dimensionedVector("zero", dimensionSet(0, 1, -1, 0, 0), vector::zero) dimensionedVector("zero", dimensionSet(0, 1, -1, 0, 0), vector::zero)
); );
volScalarField rhoeps("rhoeps", rhoRec*voidfractionRec);
rhoeps.oldTime(); // switch on saving old time
// heat transfer fields // heat transfer fields
Info << "\nCreating heat transfer fields.\n" << endl; Info << "\nCreating heat transfer fields.\n" << endl;
@ -228,3 +231,25 @@
) )
); );
weightDict.add("weights",scalarList(1,1.0)); weightDict.add("weights",scalarList(1,1.0));
dimensionedScalar TMax
(
dimensionedScalar::lookupOrDefault
(
"TMax",
transportProps,
dimTemperature,
GREAT
)
);
dimensionedScalar TMin
(
dimensionedScalar::lookupOrDefault
(
"TMin",
transportProps,
dimTemperature,
0.0
)
);

View File

@ -98,7 +98,7 @@ int main(int argc, char *argv[])
particleCloud.clockM().start(26,"Flow"); particleCloud.clockM().start(26,"Flow");
#include "updateRho.H" #include "updateRho.H"
#include "TEqImp.H" #include "TEqn.H"
particleCloud.clockM().stop("Flow"); particleCloud.clockM().stop("Flow");
stepCounter++; stepCounter++;

View File

@ -1 +1,2 @@
rhoRec = pRec / (T * R); dimensionedScalar Tave = T.weightedAverage(voidfractionRec);
rhoRec = pRec / (Tave * R);

View File

@ -12,6 +12,7 @@ EXE_INC = \
-I$(CFDEM_SRC_DIR)/lagrangian/cfdemParticle/cfdTools \ -I$(CFDEM_SRC_DIR)/lagrangian/cfdemParticle/cfdTools \
-I$(CFDEM_SRC_DIR)/recurrence/lnInclude \ -I$(CFDEM_SRC_DIR)/recurrence/lnInclude \
-I$(CFDEM_SRC_DIR)/lagrangian/cfdemParticle/derived/cfdemCloudRec \ -I$(CFDEM_SRC_DIR)/lagrangian/cfdemParticle/derived/cfdemCloudRec \
-Wno-deprecated-copy
EXE_LIBS = \ EXE_LIBS = \
-L$(CFDEM_LIB_DIR)\ -L$(CFDEM_LIB_DIR)\
@ -24,4 +25,4 @@ EXE_LIBS = \
-lfvOptions \ -lfvOptions \
-l$(CFDEM_LIB_NAME) \ -l$(CFDEM_LIB_NAME) \
$(CFDEM_ADD_LIB_PATHS) \ $(CFDEM_ADD_LIB_PATHS) \
$(CFDEM_ADD_LIBS) $(CFDEM_ADD_LIBS)

View File

@ -60,9 +60,4 @@
thermo.correct(); thermo.correct();
Info<< "T max/min : " << max(T).value() << " " << min(T).value() << endl; Info<< "T max/min : " << max(T).value() << " " << min(T).value() << endl;
particleCloud.clockM().start(31,"energySolve");
particleCloud.solve();
particleCloud.clockM().stop("energySolve");
} }

View File

@ -59,9 +59,4 @@
thermo.correct(); thermo.correct();
Info<< "T max/min : " << max(T).value() << " " << min(T).value() << endl; Info<< "T max/min : " << max(T).value() << " " << min(T).value() << endl;
particleCloud.clockM().start(31,"energySolve");
particleCloud.solve();
particleCloud.clockM().stop("energySolve");
} }

View File

@ -27,6 +27,7 @@ EXE_INC = \
-I$(LIB_SRC)/ODE/lnInclude \ -I$(LIB_SRC)/ODE/lnInclude \
-I$(LIB_SRC)/combustionModels/lnInclude \ -I$(LIB_SRC)/combustionModels/lnInclude \
-I$(CFDEM_SRC_DIR)/recurrence/lnInclude \ -I$(CFDEM_SRC_DIR)/recurrence/lnInclude \
-Wno-deprecated-copy
EXE_LIBS = \ EXE_LIBS = \
-L$(CFDEM_LIB_DIR)\ -L$(CFDEM_LIB_DIR)\

View File

@ -12,6 +12,7 @@ EXE_INC = \
-I$(CFDEM_SRC_DIR)/lagrangian/cfdemParticle/cfdTools \ -I$(CFDEM_SRC_DIR)/lagrangian/cfdemParticle/cfdTools \
-I$(CFDEM_SRC_DIR)/recurrence/lnInclude \ -I$(CFDEM_SRC_DIR)/recurrence/lnInclude \
-I$(CFDEM_SRC_DIR)/lagrangian/cfdemParticle/derived/cfdemCloudRec \ -I$(CFDEM_SRC_DIR)/lagrangian/cfdemParticle/derived/cfdemCloudRec \
-Wno-deprecated-copy
EXE_LIBS = \ EXE_LIBS = \
-L$(CFDEM_LIB_DIR)\ -L$(CFDEM_LIB_DIR)\

View File

@ -37,11 +37,19 @@ Application
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
void findPairs(labelList &, labelList &, labelPairList &); void findPairs(labelList &, labelList &, labelPairList &);
void findPairsUnordered(labelList &, labelList &, labelPairList &); void findPairsUnordered(labelList &, labelList &, labelPairList &);
void fillEmptyCells(fvMesh &, label, label, labelList &, volVectorField &, volVectorField &, scalarList &, volVectorField &, volVectorField &, bool, scalar); void fillEmptyCells(fvMesh &, label, label, scalarList &, volVectorField &, volVectorField &, scalarList &, volVectorField &, volVectorField &, bool, scalar);
void nearestNeighborCells(fvMesh &, label, label, label, labelList &, labelList &); void nearestNeighborCells(fvMesh &, label, label, label, scalarList &, labelList &);
void normalizeFields(labelList &, volVectorField &, volVectorField &); void normalizeFields(scalarList &, volVectorField &, volVectorField &);
void readDump(std::string, labelList &, vectorList &); void readDump(std::string, labelList &, scalarList &, vectorList &);
scalar weightFun(scalar); scalar weightFun(scalar);
label maxNumParticles = 1000000;
scalar minVol = 1e-12;
scalar Pi43 = 4.1888;
label posIndex = -1;
label posRad = -1;
label posX = -1;
label posY = -1;
label posZ = -1;
int main(int argc, char *argv[]) int main(int argc, char *argv[])
{ {
@ -88,6 +96,11 @@ int main(int argc, char *argv[])
label dumpIndexDisplacementIncrement(readLabel(displacementProperties.lookup("dumpIndexDisplacementIncrement"))); label dumpIndexDisplacementIncrement(readLabel(displacementProperties.lookup("dumpIndexDisplacementIncrement")));
label nNeighMin(readLabel(displacementProperties.lookup("nNeighMin"))); label nNeighMin(readLabel(displacementProperties.lookup("nNeighMin")));
label maxSearchLayers(displacementProperties.lookupOrDefault<label>("maxSearchLayers",0)); label maxSearchLayers(displacementProperties.lookupOrDefault<label>("maxSearchLayers",0));
posIndex = readLabel(displacementProperties.lookup("posIndex"));
posRad = readLabel(displacementProperties.lookup("posRad"));
posX = readLabel(displacementProperties.lookup("posX"));
posY = readLabel(displacementProperties.lookup("posY"));
posZ = readLabel(displacementProperties.lookup("posZ"));
scalar timePerInputStep(readScalar(displacementProperties.lookup("timePerInputStep"))); scalar timePerInputStep(readScalar(displacementProperties.lookup("timePerInputStep")));
scalar timePerDisplacementStep(readScalar(displacementProperties.lookup("timePerDisplacementStep"))); scalar timePerDisplacementStep(readScalar(displacementProperties.lookup("timePerDisplacementStep")));
scalar startTime(readScalar(displacementProperties.lookup("startTime"))); scalar startTime(readScalar(displacementProperties.lookup("startTime")));
@ -95,7 +108,7 @@ int main(int argc, char *argv[])
std::string fileext=string(displacementProperties.lookupOrDefault<string>("fileextension","")); std::string fileext=string(displacementProperties.lookupOrDefault<string>("fileextension",""));
bool interpolate=bool(displacementProperties.lookupOrDefault<bool>("fillEmptyCells",true)); bool interpolate=bool(displacementProperties.lookupOrDefault<bool>("fillEmptyCells",true));
bool averageMode=bool(displacementProperties.lookupOrDefault<bool>("averageMode",false)); bool averageMode=bool(displacementProperties.lookupOrDefault<bool>("averageMode",false));
volVectorField defaultUs volVectorField defaultUs
( (
IOobject IOobject
@ -110,11 +123,11 @@ int main(int argc, char *argv[])
dimensionedVector("zero", dimensionSet(0,1,-1,0,0), vector::zero) dimensionedVector("zero", dimensionSet(0,1,-1,0,0), vector::zero)
); );
volVectorField defaultUsDirectedVariance volVectorField defaultUsDirectedStdDev
( (
IOobject IOobject
( (
"defaultUDispDirectedVariance", "defaultUDispDirectedStdDev",
runTime.timeName(), runTime.timeName(),
mesh, mesh,
IOobject::READ_IF_PRESENT, IOobject::READ_IF_PRESENT,
@ -172,11 +185,11 @@ int main(int argc, char *argv[])
dimensionedVector("zero", dimensionSet(0,1,-1,0,0), vector::zero) dimensionedVector("zero", dimensionSet(0,1,-1,0,0), vector::zero)
); );
volVectorField UsDirectedVariance volVectorField UsDirectedStdDev
( (
IOobject IOobject
( (
"UDispDirectedVariance", "UDispDirectedStdDev",
runTime.timeName(), runTime.timeName(),
mesh, mesh,
IOobject::NO_READ, IOobject::NO_READ,
@ -186,7 +199,7 @@ int main(int argc, char *argv[])
dimensionedVector("zero", dimensionSet(0,1,-1,0,0), vector::zero) dimensionedVector("zero", dimensionSet(0,1,-1,0,0), vector::zero)
); );
labelList particlesInCell(mesh.nCells(), 0); scalarList particleVolInCell(mesh.nCells(), 0.0);
scalar currTime=startTime + thisProc * timePerInputStep; scalar currTime=startTime + thisProc * timePerInputStep;
label timeIndex=thisProc; label timeIndex=thisProc;
@ -196,6 +209,7 @@ int main(int argc, char *argv[])
runTime.setTime(currTime,timeIndex); runTime.setTime(currTime,timeIndex);
// read dump files and check which particle indices are present in both // read dump files and check which particle indices are present in both
labelList indices1, indices2; labelList indices1, indices2;
scalarList radii1, radii2;
vectorList positions1, positions2; vectorList positions1, positions2;
std::stringstream ss; std::stringstream ss;
@ -209,13 +223,13 @@ int main(int argc, char *argv[])
{ {
if (averageMode) if (averageMode)
{ {
normalizeFields(particlesInCell, Us, UsDirectedVariance); normalizeFields(particleVolInCell, Us, UsDirectedStdDev);
fillEmptyCells(mesh,nNeighMin,maxSearchLayers,particlesInCell,Us,UsDirectedVariance,boundaries,defaultUs,defaultUsDirectedVariance,interpolate,timePerDisplacementStep); fillEmptyCells(mesh,nNeighMin,maxSearchLayers,particleVolInCell,Us,UsDirectedStdDev,boundaries,defaultUs,defaultUsDirectedStdDev,interpolate,timePerDisplacementStep);
Us /= timePerDisplacementStep; Us /= timePerDisplacementStep;
UsDirectedVariance /= timePerDisplacementStep; UsDirectedStdDev /= timePerDisplacementStep;
Us.write(); Us.write();
UsDirectedVariance.write(); UsDirectedStdDev.write();
} }
break; break;
} }
@ -225,8 +239,8 @@ int main(int argc, char *argv[])
Info << "\t" << filename2 << endl; Info << "\t" << filename2 << endl;
Info << "corresponding to time = " << currTime << "." << endl; Info << "corresponding to time = " << currTime << "." << endl;
readDump(filename1, indices1, positions1); readDump(filename1, indices1, radii1, positions1);
readDump(filename2, indices2, positions2); readDump(filename2, indices2, radii2, positions2);
labelPairList pairs; labelPairList pairs;
findPairs(indices1,indices2,pairs); findPairs(indices1,indices2,pairs);
@ -234,15 +248,16 @@ int main(int argc, char *argv[])
// average particle displacements and their variance // average particle displacements and their variance
Info << "Binning particle displacements on mesh." << endl; Info << "Binning particle displacements on mesh." << endl;
vector position, displacement; vector position, displacement;
scalar radius, volume;
label line1, line2; label line1, line2;
label cellI; label cellI;
if (!averageMode) if (!averageMode)
{ {
Us *= 0.0; Us *= 0.0;
UsDirectedVariance *= 0.0; UsDirectedStdDev *= 0.0;
particlesInCell.clear(); particleVolInCell.clear();
particlesInCell.setSize(mesh.nCells(), 0); particleVolInCell.setSize(mesh.nCells(), 0);
} }
for (label partI = 0; partI < pairs.size(); partI++) for (label partI = 0; partI < pairs.size(); partI++)
@ -250,27 +265,29 @@ int main(int argc, char *argv[])
line1 = pairs[partI].first(); line1 = pairs[partI].first();
line2 = pairs[partI].second(); line2 = pairs[partI].second();
position = positions1[line1]; position = positions1[line1];
displacement = positions2[line2] - positions1[line1];
cellI = mesh.findCell(position); cellI = mesh.findCell(position);
if (cellI < 0) continue; if (cellI < 0) continue;
particlesInCell[cellI] += 1; displacement = positions2[line2] - positions1[line1];
Us[cellI] += displacement; radius = radii1[line1];
volume = Pi43 * radius * radius * radius;
particleVolInCell[cellI] += volume;
Us[cellI] += displacement*volume;
for (label comp=0;comp<3;comp++) for (label comp=0;comp<3;comp++)
{ {
UsDirectedVariance[cellI].component(comp) += displacement.component(comp)*displacement.component(comp); UsDirectedStdDev[cellI].component(comp) += displacement.component(comp)*displacement.component(comp)*volume;
} }
} }
if (!averageMode) if (!averageMode)
{ {
normalizeFields(particlesInCell, Us, UsDirectedVariance); normalizeFields(particleVolInCell, Us, UsDirectedStdDev);
fillEmptyCells(mesh,nNeighMin,maxSearchLayers,particlesInCell,Us,UsDirectedVariance,boundaries,defaultUs,defaultUsDirectedVariance,interpolate,timePerDisplacementStep); fillEmptyCells(mesh,nNeighMin,maxSearchLayers,particleVolInCell,Us,UsDirectedStdDev,boundaries,defaultUs,defaultUsDirectedStdDev,interpolate,timePerDisplacementStep);
Us /= timePerDisplacementStep; Us /= timePerDisplacementStep;
UsDirectedVariance /= timePerDisplacementStep; UsDirectedStdDev /= timePerDisplacementStep;
Us.write(); Us.write();
UsDirectedVariance.write(); UsDirectedStdDev.write();
} }
if (averageMode && monitorProbes) if (averageMode && monitorProbes)
@ -280,7 +297,7 @@ int main(int argc, char *argv[])
{ {
vector pos = probePoints[p]; vector pos = probePoints[p];
label cellP = mesh.findCell(pos); label cellP = mesh.findCell(pos);
monitoringDataFile << " " << particlesInCell[cellP] << " " << Us[cellP]/timePerDisplacementStep << " " << UsDirectedVariance[cellP]/(timePerDisplacementStep*timePerDisplacementStep); monitoringDataFile << " " << particleVolInCell[cellP] << " " << Us[cellP]/timePerDisplacementStep << " " << UsDirectedStdDev[cellP]/(timePerDisplacementStep*timePerDisplacementStep);
} }
monitoringDataFile << endl; monitoringDataFile << endl;
} }
@ -293,30 +310,69 @@ int main(int argc, char *argv[])
return 0; return 0;
} }
void readDump(std::string filename, labelList &indices, vectorList &positions) void readDump(std::string filename, labelList &indices, scalarList &radii, vectorList &positions)
{ {
#include <fstream> #include <fstream>
const label leadingLines = 9; const label leadingLines = 9;
label lineCounter = 0; label lineCounter = 0;
label partIndex; label partIndex;
scalar x, y, z; scalar r = 1.0, x = 0.0, y = 0.0, z = 0.0;
indices.clear(); indices.clear();
radii.clear();
positions.clear(); positions.clear();
indices.setSize(maxNumParticles);
radii.setSize(maxNumParticles);
positions.setSize(maxNumParticles);
std::ifstream file(filename); std::ifstream file(filename);
std::string str; std::string str;
std::string word;
label wordcounter;
while (std::getline(file, str)) while (std::getline(file, str))
{ {
if (lineCounter >= leadingLines) if (lineCounter >= leadingLines)
{ {
sscanf(str.c_str(), "%d %lf %lf %lf", &partIndex, &x, &y, &z); std::istringstream ss(str);
indices.append(partIndex); wordcounter = 0;
positions.append(vector(x,y,z)); while (ss >> word)
{
if (wordcounter == posIndex)
{
partIndex = stoi(word);
}
else if (wordcounter == posRad)
{
r = stod(word);
}
else if (wordcounter == posX)
{
x = stod(word);
}
else if (wordcounter == posY)
{
y = stod(word);
}
else if (wordcounter == posZ)
{
z = stod(word);
}
wordcounter++;
}
// sscanf(str.c_str(), "%d %lf %lf %lf", &partIndex, &x, &y, &z);
indices[lineCounter-leadingLines] = partIndex;
radii[lineCounter-leadingLines] = r;
positions[lineCounter-leadingLines] = vector(x,y,z);
} }
lineCounter++; lineCounter++;
} }
label readLines = lineCounter - leadingLines;
indices.resize(readLines);
radii.resize(readLines);
positions.resize(readLines);
} }
void findPairs(labelList &indices1, labelList &indices2, labelPairList &pairs) void findPairs(labelList &indices1, labelList &indices2, labelPairList &pairs)
@ -324,6 +380,10 @@ void findPairs(labelList &indices1, labelList &indices2, labelPairList &pairs)
// remove all entries from first list if they are not present in second list // remove all entries from first list if they are not present in second list
// this assumes ordered entries // this assumes ordered entries
pairs.clear();
pairs.setSize(maxNumParticles);
label pairCounter = 0;
if (indices2.size() == 0) return; if (indices2.size() == 0) return;
for (label i=0;i<indices1.size();i++) for (label i=0;i<indices1.size();i++)
@ -339,18 +399,23 @@ void findPairs(labelList &indices1, labelList &indices2, labelPairList &pairs)
else if (indices2[jmid] < index1) j1 = jmid; else if (indices2[jmid] < index1) j1 = jmid;
else else
{ {
pairs.append(labelPair(i,jmid)); pairs[pairCounter]=labelPair(i,jmid);
pairCounter++;
break; break;
} }
if (j2-j1 == 1) break; if (j2-j1 == 1) break;
} }
} }
pairs.resize(pairCounter);
Info << "findPairs: " << pairs.size() << " pairs found." << endl; Info << "findPairs: " << pairs.size() << " pairs found." << endl;
} }
void findPairsUnordered(labelList &indices1, labelList &indices2, labelPairList &pairs) void findPairsUnordered(labelList &indices1, labelList &indices2, labelPairList &pairs)
{ {
// remove all entries from first list if they are not present in second list // remove all entries from first list if they are not present in second list
pairs.clear();
pairs.setSize(maxNumParticles);
label pairCounter = 0;
for (label i=0;i<indices1.size();i++) for (label i=0;i<indices1.size();i++)
{ {
@ -358,15 +423,17 @@ void findPairsUnordered(labelList &indices1, labelList &indices2, labelPairList
{ {
if (indices1[i] == indices2[j]) if (indices1[i] == indices2[j])
{ {
pairs.append(labelPair(i,j)); pairs[pairCounter]=labelPair(i,j);
pairCounter++;
break; break;
} }
} }
} }
pairs.resize(pairCounter);
Info << "findPairs: " << pairs.size() << " pairs found." << endl; Info << "findPairs: " << pairs.size() << " pairs found." << endl;
} }
void fillEmptyCells(fvMesh &mesh, label nNeighMin, label maxSearchLayers, labelList &particlesInCell, volVectorField &Us, volVectorField& UsDirectedVariance,scalarList& boundaries, volVectorField &defaultUs, volVectorField &defaultUsDirectedVariance, bool interpolate, scalar dt) void fillEmptyCells(fvMesh &mesh, label nNeighMin, label maxSearchLayers, scalarList &particleVolInCell, volVectorField &Us, volVectorField& UsDirectedStdDev,scalarList& boundaries, volVectorField &defaultUs, volVectorField &defaultUsDirectedStdDev, bool interpolate, scalar dt)
{ {
labelList neighborsWithValues; labelList neighborsWithValues;
scalar neighborSqrDistance; scalar neighborSqrDistance;
@ -377,7 +444,7 @@ void fillEmptyCells(fvMesh &mesh, label nNeighMin, label maxSearchLayers, labelL
Info << "Filling empty cells." << endl; Info << "Filling empty cells." << endl;
forAll(mesh.C(), cellI) forAll(mesh.C(), cellI)
{ {
if (particlesInCell[cellI] > 0) continue; if (particleVolInCell[cellI] > minVol) continue;
vector position = mesh.C()[cellI]; vector position = mesh.C()[cellI];
label outsideBox = 0; label outsideBox = 0;
@ -388,11 +455,11 @@ void fillEmptyCells(fvMesh &mesh, label nNeighMin, label maxSearchLayers, labelL
if (outsideBox > 0 || !interpolate) if (outsideBox > 0 || !interpolate)
{ {
Us[cellI] = defaultUs[cellI]*dt; Us[cellI] = defaultUs[cellI]*dt;
UsDirectedVariance[cellI] = defaultUsDirectedVariance[cellI]*dt; UsDirectedStdDev[cellI] = defaultUsDirectedStdDev[cellI]*dt;
continue; continue;
} }
nearestNeighborCells(mesh, cellI, nNeighMin, maxSearchLayers, particlesInCell, neighborsWithValues); nearestNeighborCells(mesh, cellI, nNeighMin, maxSearchLayers, particleVolInCell, neighborsWithValues);
weightSum = 0.0; weightSum = 0.0;
weights.clear(); weights.clear();
for (label neighI=0; neighI<neighborsWithValues.size(); neighI++) for (label neighI=0; neighI<neighborsWithValues.size(); neighI++)
@ -406,13 +473,13 @@ void fillEmptyCells(fvMesh &mesh, label nNeighMin, label maxSearchLayers, labelL
{ {
weight = weights[neighI]/weightSum; weight = weights[neighI]/weightSum;
Us[cellI] += weight*Us[neighborsWithValues[neighI]]; Us[cellI] += weight*Us[neighborsWithValues[neighI]];
UsDirectedVariance[cellI] += weight*UsDirectedVariance[neighborsWithValues[neighI]]; UsDirectedStdDev[cellI] += weight*UsDirectedStdDev[neighborsWithValues[neighI]];
} }
if (neighborsWithValues.size() == 0) if (neighborsWithValues.size() == 0)
{ {
Us[cellI] = defaultUs[cellI]*dt; Us[cellI] = defaultUs[cellI]*dt;
UsDirectedVariance[cellI] = defaultUsDirectedVariance[cellI]*dt; UsDirectedStdDev[cellI] = defaultUsDirectedStdDev[cellI]*dt;
} }
// make sure no particles are placed outside of domain // make sure no particles are placed outside of domain
@ -429,7 +496,7 @@ void fillEmptyCells(fvMesh &mesh, label nNeighMin, label maxSearchLayers, labelL
} }
} }
void nearestNeighborCells(fvMesh &mesh, label refCell, label nNeighMin, label maxSearchLayers, labelList &particlesInCell, labelList &neighborsWithValues) void nearestNeighborCells(fvMesh &mesh, label refCell, label nNeighMin, label maxSearchLayers, scalarList &particleVolInCell, labelList &neighborsWithValues)
{ {
label numSearchLayers = 0; label numSearchLayers = 0;
std::set<label> neighbors; std::set<label> neighbors;
@ -455,11 +522,11 @@ void nearestNeighborCells(fvMesh &mesh, label refCell, label nNeighMin, label ma
{ {
newNeighbors.insert(adj); newNeighbors.insert(adj);
neighbors.insert(adj); neighbors.insert(adj);
if (particlesInCell[adj] > 0) neighborsWithValues.append(adj); if (particleVolInCell[adj] > minVol) neighborsWithValues.append(adj);
} }
} }
} }
numSearchLayers++; numSearchLayers++;
if (numSearchLayers > maxSearchLayers && maxSearchLayers > 0) return; if (numSearchLayers > maxSearchLayers && maxSearchLayers > 0) return;
@ -470,18 +537,18 @@ void nearestNeighborCells(fvMesh &mesh, label refCell, label nNeighMin, label ma
} }
} }
void normalizeFields(labelList& particlesInCell, volVectorField& Us, volVectorField & UsDirectedVariance) void normalizeFields(scalarList& particleVolInCell, volVectorField& Us, volVectorField & UsDirectedStdDev)
{ {
for (label cellJ = 0; cellJ<particlesInCell.size(); cellJ++) for (label cellJ = 0; cellJ<particleVolInCell.size(); cellJ++)
{ {
if (particlesInCell[cellJ] > 0) if (particleVolInCell[cellJ] > minVol)
{ {
Us[cellJ] /= particlesInCell[cellJ]; Us[cellJ] /= particleVolInCell[cellJ];
UsDirectedVariance[cellJ] /= particlesInCell[cellJ]; UsDirectedStdDev[cellJ] /= particleVolInCell[cellJ];
for (label comp=0;comp<3;comp++) for (label comp=0;comp<3;comp++)
{ {
UsDirectedVariance[cellJ].component(comp) -= Us[cellJ].component(comp)*Us[cellJ].component(comp); UsDirectedStdDev[cellJ].component(comp) -= Us[cellJ].component(comp)*Us[cellJ].component(comp);
if (UsDirectedVariance[cellJ].component(comp) > 0) UsDirectedVariance[cellJ].component(comp) = Foam::sqrt(UsDirectedVariance[cellJ].component(comp)); if (UsDirectedStdDev[cellJ].component(comp) > 0) UsDirectedStdDev[cellJ].component(comp) = Foam::sqrt(UsDirectedStdDev[cellJ].component(comp));
} }
} }
} }

View File

@ -124,6 +124,7 @@ particleDeformation,
potentialRelaxation, potentialRelaxation,
"surfaceTensionForce"_forceModel_surfaceTensionForce.html, "surfaceTensionForce"_forceModel_surfaceTensionForce.html,
terminalVelocity, terminalVelocity,
"transferFluidProperties"_forceModel_transferFluidProperties.html,
turbulentDispersion, turbulentDispersion,
turbulentVelocityFluctuations, turbulentVelocityFluctuations,
"virtualMassForce"_forceModel_virtualMassForce.html, "virtualMassForce"_forceModel_virtualMassForce.html,

View File

@ -23,17 +23,19 @@ ParmarBassetForceProps
nIntegral scalar1; nIntegral scalar1;
discretisationOrder scalar2; discretisationOrder scalar2;
treatForceExplicit switch1; treatForceExplicit switch1;
interpolation switch2; verbose switch2;
interpolation switch3;
smoothingModel "smoothingModel"; smoothingModel "smoothingModel";
\} :pre \} :pre
{U} = name of the finite volume fluid velocity field :ulb,l {U} = name of the finite volume fluid velocity field :ulb,l
{Us} = name of the finite volume cell averaged particle velocity field :l {Us} = name of the finite volume cell averaged particle velocity field :l
{scalar1} = number of timesteps considered in the near history :l {scalar1} = number of timesteps considered in the near history (integer > 1):l
{scalar2} = (1 or 2) discretisation order of the far history differential equations :l {scalar2} = (optional, default 1) discretisation order of the far history differential equations (1 or 2) :l
{switch1} = (optional, default true) sub model switch, see "forceSubModel"_forceSubModel.html for details :l {switch1} = (optional, default true) sub model switch, see "forceSubModel"_forceSubModel.html for details :l
{switch2} = (optional, default false) sub model switch, see "forceSubModel"_forceSubModel.html for details :l {switch2} = (optional, default false) sub model switch, see "forceSubModel"_forceSubModel.html for details :l
{smoothingModel} = name of smoothing model for the dU/dt field :l {switch3} = (optional, default false) sub model switch, see "forceSubModel"_forceSubModel.html for details :l
{smoothingModel} = name of smoothing model for the dUrel/dt field :l
:ule :ule
[Examples:] [Examples:]

View File

@ -0,0 +1,42 @@
"CFDEMproject Website"_lws - "Main Page"_main :c
:link(lws,http://www.cfdem.com)
:link(main,CFDEMcoupling_Manual.html)
:line
forceModel transferFluidProperties command :h3
[Syntax:]
Defined in "couplingProperties"_CFDEMcoupling_dicts.html#couplingProperties
dictionary.
forceModels
(
transferFluidProperties
);
transferFluidPropertiesProps
\{
verbose switch1;
interpolation switch2;
\} :pre
{switch1} = (optional, default false) sub model switch, see "forceSubModel"_forceSubModel.html for details :ulb,l
{switch2} = (optional, default false) sub model switch, see "forceSubModel"_forceSubModel.html for details :l
:ule
[Description:]
This "force model" does not influence the particles or the flow - it transfer to fluid density and (dynamic)
viscosity from OpenFOAM to LIGGGHTS.
[Restrictions:]
This model requires {fix cfd/coupling/fluidproperties} to work.
[Related commands:]
"forceModel"_forceModel.html

View File

@ -15,17 +15,22 @@ dictionary.
smoothingModel constDiffSmoothing; smoothingModel constDiffSmoothing;
constDiffSmoothingProps constDiffSmoothingProps
\{ \{
lowerLimit number1; lowerLimit number1;
upperLimit number2; upperLimit number2;
smoothingLength lengthScale; smoothingLength lengthScale;
smoothingLengthReferenceField lengthScaleRefField; smoothingLengthReference lengthScaleRef;
smoothingLengthFieldName fieldName1;
smoothingLengthReferenceFieldName fieldName2;
verbose; verbose;
\} :pre \} :pre
{number1} = scalar fields will be bound to this lower value :ulb,l {number1} = scalar fields will be bound to this lower value :ulb,l
{number2} = scalar fields will be bound to this upper value :l {number2} = scalar fields will be bound to this upper value :l
{lengthScale} = length scale over which the exchange fields will be smoothed out :l {lengthScale} = length scale over which the exchange fields will be smoothed out :l
{lengthScaleRefField} = length scale over which reference fields (e.g., the average particle velocity) will be smoothed out. Should be always larger than lengthScale. If not specified, will be equal to lengthScale. :l {lengthScaleRef} = (optional) length scale over which reference fields (e.g., the average particle velocity) will be smoothed out. Should be always larger than lengthScale. If not specified, will be equal to lengthScale. :l
{fieldName1} = (optional) name of scalar field to be used as local smoothing length. :l
{fieldName2} = (optional) name of scalar field to be used as local smoothing length for reference fields. :l
{verbose} = (optional, default false) flag for debugging output :l {verbose} = (optional, default false) flag for debugging output :l
:ule :ule
@ -51,6 +56,11 @@ which these reference fields are not specified. Values calculated in the cells
e.g. the average particle velocity, which are not specified in all cells in case e.g. the average particle velocity, which are not specified in all cells in case
the flow is rather dilute. the flow is rather dilute.
Alternative to {smoothingLength} and {smoothingLengthReference},
{smoothingLengthFieldName} and/or {smoothingLengthReferenceFieldName} can be used
to define spatial variation of the smoothing lengths. Either the scalar or field
options must be used, giving both will result in errors.
[Restrictions:] [Restrictions:]
This model is tested in a limited number of flow situations. This model is tested in a limited number of flow situations.

View File

@ -3,4 +3,4 @@ lagrangian/cfdemParticleComp/dir
recurrence/dir recurrence/dir
finiteVolume/dir finiteVolume/dir
../applications/solvers/cfdemSolverMultiphase/multiphaseMixture/dir ../applications/solvers/cfdemSolverMultiphase/multiphaseMixture/dir
../applications/solvers/cfdemSolverMultiphaseScalar/multiphaseMixture/dir ../applications/solvers/cfdemSolverMultiphaseScalar/multiphaseMixtureScalar/dir

View File

@ -96,6 +96,7 @@ $(forceModels)/potentialRelaxation/potentialRelaxation.C
$(forceModels)/BeetstraDrag/BeetstraDrag.C $(forceModels)/BeetstraDrag/BeetstraDrag.C
$(forceModels)/BeetstraDragPoly/BeetstraDragPoly.C $(forceModels)/BeetstraDragPoly/BeetstraDragPoly.C
$(forceModels)/dSauter/dSauter.C $(forceModels)/dSauter/dSauter.C
$(forceModels)/transferFluidProperties/transferFluidProperties.C
$(forceModels)/Fines/Fines.C $(forceModels)/Fines/Fines.C
$(forceModels)/Fines/FinesFields.C $(forceModels)/Fines/FinesFields.C
$(forceModels)/Fines/FanningDynFines.C $(forceModels)/Fines/FanningDynFines.C

View File

@ -274,6 +274,8 @@ bool cfdemCloudEnergy::evolve
void cfdemCloudEnergy::postFlow() void cfdemCloudEnergy::postFlow()
{ {
if (ignore()) return;
cfdemCloud::postFlow(); cfdemCloud::postFlow();
forAll(energyModel_, modeli) forAll(energyModel_, modeli)
{ {
@ -285,18 +287,6 @@ void cfdemCloudEnergy::postFlow()
} }
} }
void cfdemCloudEnergy::solve()
{
forAll(energyModel_, modeli)
{
energyModel_[modeli].solve();
}
forAll(massTransferModel_, modeli)
{
massTransferModel_[modeli].solve();
}
}
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
} // End namespace Foam } // End namespace Foam

View File

@ -42,7 +42,7 @@ namespace Foam
class energyModel; class energyModel;
class massTransferModel; class massTransferModel;
class thermCondModel; class thermCondModel;
class diffCoeffModel; class diffCoeffModel;
class chemistryModel; class chemistryModel;
/*---------------------------------------------------------------------------*\ /*---------------------------------------------------------------------------*\
Class cfdemCloudEnergy Declaration Class cfdemCloudEnergy Declaration
@ -142,8 +142,6 @@ public:
void postFlow(); void postFlow();
void solve();
}; };

View File

@ -100,6 +100,7 @@ void One2One::setup
comm_ comm_
); );
// count number of receives
ncollected_ = 0; ncollected_ = 0;
int nrequests = 0; int nrequests = 0;
for (int i = 0; i < nsrc_procs_; i++) for (int i = 0; i < nsrc_procs_; i++)
@ -115,6 +116,18 @@ void One2One::setup
} }
} }
// count number of sends
if (nlocal_ > 0)
{
for (int i = 0; i < ndst_procs_; i++)
{
if (dst_procs_[i] != me_)
{
nrequests++;
}
}
}
if (nrequests > 0) if (nrequests > 0)
{ {
request_ = new MPI_Request[nrequests]; request_ = new MPI_Request[nrequests];
@ -143,23 +156,27 @@ void One2One::exchange(T *&src, T *&dst, int data_length)
{ {
if (src_procs_[i] != me_) if (src_procs_[i] != me_)
{ {
#ifdef O2ODEBUG int tag = (src_procs_[i] << 16) | me_;
std::cout<< "[" << me_ << "]"
<< " RCV " << i #ifdef O2ODEBUG
<< " of " << nsrc_procs_ std::cout<< "[" << me_ << "]"
<< " from: " << src_procs_[i] << " RCV " << (i+1)
<< " natoms_[src_procs_[i]] " << natoms_[src_procs_[i]] << " of " << nsrc_procs_
<< " datalength " << data_length << " from: " << src_procs_[i]
<< " offset " << offset << " natoms_[src_procs_[i]] " << natoms_[src_procs_[i]]
<< std::endl; << " data_length " << data_length
#endif << " offset " << offset
<< " tag " << tag
<< std::endl;
#endif
MPI_Irecv MPI_Irecv
( (
&dst[offset], &dst[offset],
natoms_[src_procs_[i]]*data_length, natoms_[src_procs_[i]]*data_length,
wrap.mpi_type, wrap.mpi_type,
src_procs_[i], src_procs_[i],
MPI_ANY_TAG, tag,
comm_, comm_,
&request_[requesti] &request_[requesti]
); );
@ -168,16 +185,34 @@ void One2One::exchange(T *&src, T *&dst, int data_length)
else // data is available on-proc else // data is available on-proc
{ {
offset_local = offset; offset_local = offset;
#ifdef O2ODEBUG
std::cout<< "[" << me_ << "]"
<< " RCV " << (i+1)
<< " of " << nsrc_procs_
<< " from: " << src_procs_[i]
<< " skipped (self)"
<< " offset_local " << offset_local
<< std::endl;
#endif
} }
} }
#ifdef O2ODEBUG
else
{
std::cout<< "[" << me_ << "]"
<< " RCV " << (i+1)
<< " of " << nsrc_procs_
<< " from: " << src_procs_[i]
<< " skipped (no data)"
<< std::endl;
}
#endif
offset += natoms_[src_procs_[i]]*data_length; offset += natoms_[src_procs_[i]]*data_length;
} }
// make sure all receives are posted // nonblocking sends
MPI_Barrier(comm_);
// blocking sends - do nonblocking instead
// since doing many-2-many here?
// only do sends if I have particles // only do sends if I have particles
if (nlocal_ > 0) if (nlocal_ > 0)
{ {
@ -185,29 +220,62 @@ void One2One::exchange(T *&src, T *&dst, int data_length)
{ {
if (dst_procs_[i] != me_) if (dst_procs_[i] != me_)
{ {
#ifdef O2ODEBUG int tag = (me_ << 16) | dst_procs_[i];
std::cout<< "[" << me_ << "]"
<< " SEND to: " << dst_procs_[i] #ifdef O2ODEBUG
<< " nlocal_ " << nlocal_ std::cout<< "[" << me_ << "]"
<< " data_length " << data_length << " SEND to: " << dst_procs_[i]
<< std::endl; << " nlocal_ " << nlocal_
#endif << " data_length " << data_length
MPI_Send << " tag " << tag
<< std::endl;
#endif
MPI_Isend
( (
src, src,
nlocal_*data_length, nlocal_*data_length,
wrap.mpi_type, wrap.mpi_type,
dst_procs_[i], dst_procs_[i],
0, tag,
comm_ comm_,
&request_[requesti]
); );
requesti++;
} }
#ifdef O2ODEBUG
else
{
std::cout<< "[" << me_ << "]"
<< " SEND to: " << dst_procs_[i]
<< " skipped (self)" << std::endl;
}
#endif
} }
} }
#ifdef O2ODEBUG
else
{
std::cout<< "[" << me_ << "]" << " SEND skipped (no data)" << std::endl;
}
#endif
// only wait if requests were actually posted // only wait if requests were actually posted
if (requesti > 0) if (requesti > 0)
{
#ifdef O2ODEBUG
std::cout<< "[" << me_ << "]"
<< " WAIT for: " << requesti << " requests" << std::endl;
#endif
MPI_Waitall(requesti, request_, status_); MPI_Waitall(requesti, request_, status_);
}
#ifdef O2ODEBUG
else
{
std::cout<< "[" << me_ << "]" << " WAIT skipped (no requests)" << std::endl;
}
#endif
// copy on-proc data // copy on-proc data
if (offset_local > -1) if (offset_local > -1)
@ -223,6 +291,13 @@ void One2One::exchange(T *&src, T *&dst, int data_length)
dst[locali+offset_local] = src[locali]; dst[locali+offset_local] = src[locali];
} }
} }
// wait for all procs to complete data exchange
#ifdef O2ODEBUG
std::cout<< "[" << me_ << "] BARRIER" << std::endl;
#endif
MPI_Barrier(comm_);
} }
template void One2One::exchange<int>(int*&, int*&, int); template void One2One::exchange<int>(int*&, int*&, int);

View File

@ -183,6 +183,7 @@ void twoWayOne2One::createProcMap()
point(ligbb[0][0], ligbb[0][1], ligbb[0][2]), point(ligbb[0][0], ligbb[0][1], ligbb[0][2]),
point(ligbb[1][0], ligbb[1][1], ligbb[1][2]) point(ligbb[1][0], ligbb[1][1], ligbb[1][2])
); );
delete [] ligbb;
if (boundBoxMargin_ > 0.) if (boundBoxMargin_ > 0.)
{ {
thisLigBox.max() = thisLigBox.max() + boundBoxMargin_ * vector::one; thisLigBox.max() = thisLigBox.max() + boundBoxMargin_ * vector::one;
@ -230,6 +231,7 @@ twoWayOne2One::~twoWayOne2One()
{ {
delete foam2lig_; delete foam2lig_;
delete lig2foam_; delete lig2foam_;
delete [] lig2foam_mask_;
destroy(lig2foam_ids_); destroy(lig2foam_ids_);
destroy(foam2lig_ids_); destroy(foam2lig_ids_);
@ -777,10 +779,7 @@ void twoWayOne2One::locateParticles()
lig2foam_->exchange(my_prev_cell_ids, prev_cell_ids_); lig2foam_->exchange(my_prev_cell_ids, prev_cell_ids_);
} }
if (lig2foam_mask_) delete [] lig2foam_mask_;
{
delete [] lig2foam_mask_;
}
lig2foam_mask_ = new bool[lig2foam_->ncollected_]; lig2foam_mask_ = new bool[lig2foam_->ncollected_];
DynamicList<label> cellIds; DynamicList<label> cellIds;

View File

@ -105,8 +105,6 @@ public:
virtual void postFlow() {} virtual void postFlow() {}
virtual void solve() {}
const volScalarField& kf0Field() const; const volScalarField& kf0Field() const;
const volScalarField& CpField() const; const volScalarField& CpField() const;
@ -116,7 +114,6 @@ public:
return 0.0; return 0.0;
} }
}; };

View File

@ -77,7 +77,6 @@ BeetstraDrag::BeetstraDrag
particleCloud_.probeM().vectorFields_.append("dragForce"); //first entry must be the force particleCloud_.probeM().vectorFields_.append("dragForce"); //first entry must be the force
particleCloud_.probeM().vectorFields_.append("Urel"); particleCloud_.probeM().vectorFields_.append("Urel");
particleCloud_.probeM().scalarFields_.append("Rep"); particleCloud_.probeM().scalarFields_.append("Rep");
particleCloud_.probeM().scalarFields_.append("betaP");
particleCloud_.probeM().scalarFields_.append("voidfraction"); particleCloud_.probeM().scalarFields_.append("voidfraction");
particleCloud_.probeM().writeHeader(); particleCloud_.probeM().writeHeader();

View File

@ -34,7 +34,6 @@ Description
#include "ParmarBassetForce.H" #include "ParmarBassetForce.H"
#include "addToRunTimeSelectionTable.H" #include "addToRunTimeSelectionTable.H"
#include "smoothingModel.H" #include "smoothingModel.H"
#include "constDiffSmoothing.H"
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
@ -71,17 +70,18 @@ ParmarBassetForce::ParmarBassetForce
U_(sm.mesh().lookupObject<volVectorField> (velFieldName_)), U_(sm.mesh().lookupObject<volVectorField> (velFieldName_)),
UsFieldName_(propsDict_.lookup("granVelFieldName")), UsFieldName_(propsDict_.lookup("granVelFieldName")),
Us_(sm.mesh().lookupObject<volVectorField> (UsFieldName_)), Us_(sm.mesh().lookupObject<volVectorField> (UsFieldName_)),
nInt_(readLabel(propsDict_.lookup("nIntegral"))), nInt_(propsDict_.lookupOrDefault<int>("nIntegral", -1)),
discOrder_(readLabel(propsDict_.lookup("discretisationOrder"))), discOrder_(propsDict_.lookupOrDefault<int>("discretisationOrder", 1)),
nHist_(nInt_+discOrder_+1), ddtUrelHistSize_(nInt_+discOrder_),
FHistSize_(2*discOrder_+1), rHistSize_(nInt_),
ddtUrelHist_(nHist_,NULL), // UrelHist_[ndt in past][particle ID][dim] FHistSize_(2*discOrder_),
rHist_(nHist_,NULL), // rHist_[ndt in past][particle ID][0] ddtUrelHistRegName_(typeName + "ddtUrelHist"), // indexed as: ddtUrelHist_[particle ID][iDim*ddtUrelHistSize_+iHist]
FHist_(2,List<double**>(FHistSize_,NULL)), // FHist_[k={1,2}-1][ndt in past][particle ID][dim] rHistRegName_(typeName + "rHist"), // indexed as: rHist_[particle ID][iHist]
gH0_(NULL), FHistRegName_(typeName + "FHist"), // indexed as: ddtUrelHist_[particle ID][iDim*FHistSize_*2+iHist*2+k]
tRef_(NULL), gH0RegName_(typeName + "gH0"),
mRef_(NULL), tRefRegName_(typeName + "tRef"),
lRef_(NULL), mRefRegName_(typeName + "mRef"),
lRefRegName_(typeName + "lRef"),
Urel_ Urel_
( IOobject ( IOobject
( (
@ -115,12 +115,12 @@ ParmarBassetForce::ParmarBassetForce
) )
) )
{ {
// init force sub model // init force sub model
setForceSubModels(propsDict_); setForceSubModels(propsDict_);
// define switches which can be read from dict // define switches which can be read from dict
forceSubM(0).setSwitchesList(SW_TREAT_FORCE_EXPLICIT,true); // activate treatExplicit switch forceSubM(0).setSwitchesList(SW_TREAT_FORCE_EXPLICIT,true); // activate treatExplicit switch
forceSubM(0).setSwitchesList(SW_INTERPOLATION,true); // activate search for interpolate switch forceSubM(0).setSwitchesList(SW_INTERPOLATION,true); // activate search for interpolate switch
forceSubM(0).setSwitchesList(SW_VERBOSE,true); // activate search for verbose switch
forceSubM(0).readSwitches(); forceSubM(0).readSwitches();
//Extra switches/settings //Extra switches/settings
@ -129,15 +129,23 @@ ParmarBassetForce::ParmarBassetForce
if (discOrder_ < 1 || discOrder_ > 2) if (discOrder_ < 1 || discOrder_ > 2)
FatalError << "Parmar Basset Force: Discretisation order > 2 not implemented!" << abort(FatalError); FatalError << "Parmar Basset Force: Discretisation order > 2 not implemented!" << abort(FatalError);
if (nInt_ < 1)
FatalError << "Parmar Basset Force: nIntegral missing or invalid, must be > 1" << abort(FatalError);
// allocate particle properties
particleCloud_.registerParticleProperty<double**>(ddtUrelHistRegName_,3*ddtUrelHistSize_,NOTONCPU,false);
particleCloud_.registerParticleProperty<double**>( rHistRegName_, rHistSize_,NOTONCPU,false);
particleCloud_.registerParticleProperty<double**>( FHistRegName_, 6*FHistSize_,NOTONCPU,false);
particleCloud_.registerParticleProperty<double**>( gH0RegName_, 1 ,NOTONCPU,false);
particleCloud_.registerParticleProperty<double**>( tRefRegName_, 1 ,NOTONCPU,false);
particleCloud_.registerParticleProperty<double**>( mRefRegName_, 1 ,NOTONCPU,false);
particleCloud_.registerParticleProperty<double**>( lRefRegName_, 1 ,NOTONCPU,false);
//Append the field names to be probed //Append the field names to be probed
particleCloud_.probeM().initialize(typeName, typeName+".logDat"); particleCloud_.probeM().initialize(typeName, typeName+".logDat");
particleCloud_.probeM().vectorFields_.append("ParmarBassetForce"); //first entry must the be the force particleCloud_.probeM().vectorFields_.append("ParmarBassetForce"); //first entry must the be the force
particleCloud_.probeM().vectorFields_.append("Urel"); particleCloud_.probeM().vectorFields_.append("Urel");
particleCloud_.probeM().vectorFields_.append("ddtUrel"); particleCloud_.probeM().vectorFields_.append("ddtUrel");
//
particleCloud_.probeM().vectorFields_.append("UrelNoSmooth");
particleCloud_.probeM().vectorFields_.append("ddtUrelNoSmooth");
//
particleCloud_.probeM().vectorFields_.append("Fshort"); particleCloud_.probeM().vectorFields_.append("Fshort");
particleCloud_.probeM().vectorFields_.append("Flong1"); particleCloud_.probeM().vectorFields_.append("Flong1");
particleCloud_.probeM().vectorFields_.append("Flong2"); particleCloud_.probeM().vectorFields_.append("Flong2");
@ -158,20 +166,6 @@ ParmarBassetForce::ParmarBassetForce
ParmarBassetForce::~ParmarBassetForce() ParmarBassetForce::~ParmarBassetForce()
{ {
particleCloud_.dataExchangeM().destroy(gH0_, 1);
particleCloud_.dataExchangeM().destroy(tRef_, 1);
particleCloud_.dataExchangeM().destroy(mRef_, 1);
particleCloud_.dataExchangeM().destroy(lRef_, 1);
for (int i=0; i<nHist_; i++)
{
particleCloud_.dataExchangeM().destroy(ddtUrelHist_[i],3);
particleCloud_.dataExchangeM().destroy(rHist_ [i],1);
}
for (int i=0; i<FHistSize_; i++)
for (int k=0; k<2; k++)
particleCloud_.dataExchangeM().destroy(FHist_[k][i],3);
} }
@ -180,16 +174,18 @@ ParmarBassetForce::~ParmarBassetForce()
void ParmarBassetForce::setForce() const void ParmarBassetForce::setForce() const
{ {
// allocate arrays double**& ddtUrelHist_ = particleCloud_.getParticlePropertyRef<double**>(ddtUrelHistRegName_);
if(particleCloud_.numberOfParticlesChanged()) double**& rHist_ = particleCloud_.getParticlePropertyRef<double**>( rHistRegName_);
reAllocArrays(); double**& FHist_ = particleCloud_.getParticlePropertyRef<double**>( FHistRegName_);
double**& gH0_ = particleCloud_.getParticlePropertyRef<double**>( gH0RegName_);
double**& tRef_ = particleCloud_.getParticlePropertyRef<double**>( tRefRegName_);
double**& mRef_ = particleCloud_.getParticlePropertyRef<double**>( mRefRegName_);
double**& lRef_ = particleCloud_.getParticlePropertyRef<double**>( lRefRegName_);
vector position(0,0,0); vector position(0,0,0);
vector Urel(0,0,0); vector Urel(0,0,0);
vector ddtUrel(0,0,0); vector ddtUrel(0,0,0);
scalar t0min = 0.00;
const volScalarField& nufField = forceSubM(0).nuField(); const volScalarField& nufField = forceSubM(0).nuField();
const volScalarField& rhoField = forceSubM(0).rhoField(); const volScalarField& rhoField = forceSubM(0).rhoField();
@ -220,26 +216,17 @@ void ParmarBassetForce::setForce() const
Urel_ = Us_ - U_; Urel_ = Us_ - U_;
ddtUrel_ = fvc::ddt(Us_) - fvc::ddt(U_) - (Us_ & fvc::grad(U_)); ddtUrel_ = fvc::ddt(Us_) - fvc::ddt(U_) - (Us_ & fvc::grad(U_));
//
volVectorField UrelNoSmooth_ = Urel_;
volVectorField ddtUrelNoSmooth_ = ddtUrel_;
//
smoothingM().smoothen(Urel_); smoothingM().smoothen(Urel_);
smoothingM().smoothen(ddtUrel_); smoothingM().smoothen(ddtUrel_);
interpolationCellPoint<vector> UrelInterpolator_(Urel_); interpolationCellPoint<vector> UrelInterpolator_(Urel_);
interpolationCellPoint<vector> ddtUrelInterpolator_(ddtUrel_); interpolationCellPoint<vector> ddtUrelInterpolator_(ddtUrel_);
//
interpolationCellPoint<vector> UrelNoSmoothInterpolator_(UrelNoSmooth_);
interpolationCellPoint<vector> ddtUrelNoSmoothInterpolator_(ddtUrelNoSmooth_);
//
for(int index = 0;index < particleCloud_.numberOfParticles(); index++) for(int index = 0;index < particleCloud_.numberOfParticles(); index++)
{ {
vector ParmarBassetForce(0,0,0); vector ParmarBassetForce(0,0,0);
vector Fshort(0,0,0); vector Fshort(0,0,0);
vector Flong[2]={vector::zero, vector::zero};
label cellI = particleCloud_.cellIDs()[index][0]; label cellI = particleCloud_.cellIDs()[index][0];
if (cellI > -1) // particle Found if (cellI > -1) // particle Found
@ -268,12 +255,13 @@ void ParmarBassetForce::setForce() const
if (gH0_[index][0]!=NOTONCPU) if (gH0_[index][0]!=NOTONCPU)
{ {
r = pow(gH0_[index][0]/gH,1.5); // Eq. 3.4 scalar gHratio = gH0_[index][0]/gH;
r = gHratio*sqrt(gHratio); // gHratio^1.5, Eq. 3.4
if (r<0.25 || r>2.0) if (r<0.25 || r>2.0)
{ {
gH0_[index][0] = NOTONCPU; //reset reference gH0_[index][0] = NOTONCPU; //reset reference
ddtUrelHist_[0][index][0] = NOTONCPU; //reset ddtU history (only component used for checking nKnown) ddtUrelHist_[index][0] = NOTONCPU; //reset ddtU history (only component used for checking nKnown)
} }
} }
@ -285,7 +273,7 @@ void ParmarBassetForce::setForce() const
scalar Vs = rs*rs*rs*M_PI*4/3; scalar Vs = rs*rs*rs*M_PI*4/3;
scalar mRef = Vs*rhoField[cellI] * gH * 5.2863; // 9/(2*sqrt(pi))*(256/pi)^(1/6) = 5.2863 (Eq. 3.2) scalar mRef = Vs*rhoField[cellI] * gH * 5.2863; // 9/(2*sqrt(pi))*(256/pi)^(1/6) = 5.2863 (Eq. 3.2)
gH0_[index][0] = gH; gH0_[index][0] = gH;
tRef_[index][0] = tRef; tRef_[index][0] = tRef;
mRef_[index][0] = mRef; mRef_[index][0] = mRef;
lRef_[index][0] = rs; lRef_[index][0] = rs;
@ -298,29 +286,15 @@ void ParmarBassetForce::setForce() const
scalar dt = U_.mesh().time().deltaT().value() / tRef_[index][0]; // dim.less scalar dt = U_.mesh().time().deltaT().value() / tRef_[index][0]; // dim.less
scalar t0 = nInt_*dt; // dim.less scalar t0 = nInt_*dt; // dim.less
//********* update histories *********//
// non-dimensionlise // non-dimensionlise
Urel /= mps; Urel /= mps;
ddtUrel /= mpss; ddtUrel /= mpss;
// update ddtUrel and r history
update_ddtUrelHist(ddtUrel,index); // add current dim.less ddtUrel to history
update_rHist(r,index); // add current r to history
// warning and reset for too small t0
if (t0<t0min)
{
Pout << "ParmarBassetForce WARNING: t0 = " << t0 << " at ID = " << index << endl;
gH0_[index][0] = NOTONCPU; //reset reference
ddtUrelHist_[0][index][0] = NOTONCPU; //reset ddtU history (only component used for checking nKnown)
}
// check length of known history // check length of known history
int nKnown = 0; int nKnown = 1; // we always know the current step
for (int j=0; j<nHist_; j++) // loop over past times for (int j=0; j<ddtUrelHistSize_; j++) // loop over past times
{ {
if (ddtUrelHist_[j][index][0] == NOTONCPU) if (ddtUrelHist_[index][j] == NOTONCPU)
break; break;
else else
nKnown++; nKnown++;
@ -332,117 +306,92 @@ void ParmarBassetForce::setForce() const
int nShort = min(nKnown,nInt_+1); int nShort = min(nKnown,nInt_+1);
// int_0^dt K(r,xi) dxi * ddtU(t) dxi (singularity treated by assuming constant acceleration) // int_0^dt K(r,xi) dxi * ddtU(t) dxi (singularity treated by assuming constant acceleration)
if (nShort>0) for (int i=0; i<3; i++) // loop over dimensions
{ Fshort[i] = -calculateK0(r,dt) * ddtUrel[i];
for (int i=0; i<3; i++) // loop over dimensions
Fshort[i] = -calculateK0(r,dt) * ddtUrelHist_[0][index][i];
}
// int_dt^t0 K(r,xi) * ddtU(t-xi) dxi (trapezoid rule) // int_dt^t0 K(r,xi) * ddtU(t-xi) dxi (trapezoid rule)
if (nShort>2) if (nShort>2)
{ {
for (int j=1; j<nShort; j++) for (int j=0; j<(nShort-1); j++) // we don't use the current step here, hence nShort-1
{ {
scalar xi = j*dt; scalar xi = (j+1)*dt;
scalar K = pow((pow(xi,.25) + rHist_[j][index][0]*xi),-2.); // Eq. 3.4 scalar invsqrtK = sqrt(sqrt(xi)) + rHist_[index][j]*xi; // K^-0.5
scalar K = 1./(invsqrtK*invsqrtK); // Eq. 3.4
for (int i=0; i<3; i++) // loop over dimensions for (int i=0; i<3; i++) // loop over dimensions
Fshort[i] -= trapWeight(j,nShort) * K * ddtUrelHist_[j][index][i] * dt; Fshort[i] -= trapWeight(j,nShort-1) * K * ddtUrelHist_[index][i*ddtUrelHistSize_+j] * dt;
} }
} }
//********* long term force computing (differential form) *********// //********* long term force computing (differential form) *********//
// update F1, F2 history
update_FHist(vector::zero,vector::zero,index);
// initialise ddtUrel(t0) and Flong(:) as 0 and r(t0) as 1 // initialise ddtUrel(t0) and Flong(:) as 0 and r(t0) as 1
if (nKnown == nInt_) if (nKnown == nInt_)
{ {
for (int j=nInt_; j<nHist_; j++) // loop over past times // initialise the histories beyond nInt
{ for (int j=nInt_-1; j<rHistSize_; j++) // loop over past times
rHist_[j][index][0] = 1.; rHist_[index][j] = 1.;
for (int j=nInt_-1; j<ddtUrelHistSize_; j++) // loop over past times
for (int i=0; i<3; i++) // loop over dimensions for (int i=0; i<3; i++) // loop over dimensions
ddtUrelHist_[j][index][i] = 0.0; ddtUrelHist_[index][i*ddtUrelHistSize_+j] = 0.0;
}
for (int k=0; k<2; k++) // loop over F1, F2 for (int k=0; k<2; k++) // loop over F1, F2
for (int j=0; j<FHistSize_; j++) // loop over past times for (int j=0; j<FHistSize_; j++) // loop over past times
for (int i=0; i<3; i++) // loop over dimensions for (int i=0; i<3; i++) // loop over dimensions
FHist_[k][j][index][i] = 0.0; FHist_[index][i*FHistSize_*2+j*2+k] = 0.0;
nKnown = nHist_; nKnown = ddtUrelHistSize_+1;
} }
// solve ODEs // solve ODEs
if (nKnown == nHist_) if (nKnown == ddtUrelHistSize_+1)
{ {
for (int k=0; k<2; k++) // loop over F1, F2 for (int k=0; k<2; k++) // loop over F1, F2
{ {
//calculate coefficients //calculate coefficients
double C[4]; double C[4];
calculateCoeffs(k,t0,rHist_[nInt_][index][0],c,chi,C); calculateCoeffs(k,t0,rHist_[index][nInt_-1],c,chi,C);
// solve Eq. 3.20 // solve Eq. 3.20
solveFlongODE(k,C,dt,index); Flong[k] = solveFlongODE(FHist_,ddtUrelHist_,k,C,dt,index);
} }
} }
//********* update histories *********//
update_ddtUrelHist(ddtUrelHist_,ddtUrel,index); // add current dim.less ddtUrel to history
update_rHist(rHist_,r,index); // add current r to history
update_FHist(FHist_,Flong[0],Flong[1],index);
//********* total force *********// //********* total force *********//
// sum and convert to N // sum and convert to N
for (int i=0; i<3; i++) // loop over dimensions ParmarBassetForce = Fshort;
{ for (int k=0; k<2; k++) // loop over F1, F2
ParmarBassetForce[i] = Fshort[i]; ParmarBassetForce += Flong[k];
for (int k=0; k<2; k++) // loop over F1, F2
ParmarBassetForce[i] += FHist_[k][0][index][i];
}
ParmarBassetForce *= newton; ParmarBassetForce *= newton;
if (forceSubM(0).verbose() && index >= 0 && index < 2)
{
Pout << "cellI = " << cellI << endl;
Pout << "index = " << index << endl;
Pout << "Fshort = " << Fshort*newton << endl;
Pout << "Flong1 = " << Flong[0]*newton << endl;
Pout << "Flong2 = " << Flong[1]*newton << endl;
Pout << "Ftotal = " << ParmarBassetForce << endl;
}
// Set value fields and write the probe // Set value fields and write the probe
if(probeIt_) if(probeIt_)
{ {
scalar ReRef = 0.75/(gH0_[index][0]-0.105); scalar ReRef = 0.75/(gH0_[index][0]-0.105);
vector Flong1(0,0,0);
vector Flong2(0,0,0);
for (int i=0; i<3; i++) // loop over dimensions
{
Flong1[i] = FHist_[0][0][index][i];
Flong2[i] = FHist_[1][0][index][i];
}
//
// relative velocity (m/s)
vector UrelNoSmooth;
vector ddtUrelNoSmooth;
if(forceSubM(0).interpolation())
UrelNoSmooth = UrelNoSmoothInterpolator_.interpolate(position,cellI);
else
UrelNoSmooth = UrelNoSmooth_[cellI];
// acceleration (m/s2)
if(forceSubM(0).interpolation())
ddtUrelNoSmooth = ddtUrelNoSmoothInterpolator_.interpolate(position,cellI);
else
ddtUrelNoSmooth = ddtUrelNoSmooth_[cellI];
UrelNoSmooth /= mps;
ddtUrelNoSmooth /= mpss;
//
#include "setupProbeModelfields.H" #include "setupProbeModelfields.H"
vValues.append(ParmarBassetForce); //first entry must the be the force vValues.append(ParmarBassetForce); //first entry must the be the force
vValues.append(Urel); vValues.append(Urel);
vValues.append(ddtUrel); vValues.append(ddtUrel);
//
vValues.append(UrelNoSmooth);
vValues.append(ddtUrelNoSmooth);
//
vValues.append(Fshort); vValues.append(Fshort);
vValues.append(Flong1); vValues.append(Flong[0]);
vValues.append(Flong2); vValues.append(Flong[1]);
sValues.append(ReRef); sValues.append(ReRef);
sValues.append(tRef_[index][0]); sValues.append(tRef_[index][0]);
sValues.append(mRef_[index][0]); sValues.append(mRef_[index][0]);
@ -456,8 +405,8 @@ void ParmarBassetForce::setForce() const
else else
{ {
// not on CPU // not on CPU
gH0_[index][0] = NOTONCPU; //reset reference gH0_[index][0] = NOTONCPU; //reset reference
ddtUrelHist_[0][index][0] = NOTONCPU; //reset ddtU history (only component used for checking nKnown) ddtUrelHist_[index][0] = NOTONCPU; //reset ddtU history (only component used for checking nKnown)
} }
// write particle based data to global array // write particle based data to global array
@ -465,32 +414,11 @@ void ParmarBassetForce::setForce() const
} }
} }
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
void Foam::ParmarBassetForce::reAllocArrays() const
{
Pout << "ParmarBassetForce::reAllocArrays..." << endl;
particleCloud_.dataExchangeM().allocateArray(gH0_, NOTONCPU,1);
particleCloud_.dataExchangeM().allocateArray(tRef_, NOTONCPU,1);
particleCloud_.dataExchangeM().allocateArray(mRef_, NOTONCPU,1);
particleCloud_.dataExchangeM().allocateArray(lRef_, NOTONCPU,1);
for (int i=0; i<nHist_; i++)
{
particleCloud_.dataExchangeM().allocateArray(ddtUrelHist_[i],NOTONCPU,3);
particleCloud_.dataExchangeM().allocateArray(rHist_ [i],NOTONCPU,1);
}
for (int i=0; i<2*discOrder_+1; i++)
for (int k=0; k<2; k++)
particleCloud_.dataExchangeM().allocateArray(FHist_[k][i],0.0,3);
}
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
scalar Foam::ParmarBassetForce::calculateK0(scalar r, scalar dt) const scalar Foam::ParmarBassetForce::calculateK0(scalar r, scalar dt) const
{ {
scalar cbrtr = cbrt(r); // cube root of r scalar cbrtr = cbrt(r); // cube root of r
scalar gamma = cbrtr*pow(dt,0.25); scalar gamma = cbrtr*sqrt(sqrt(dt));
/* /*
scalar K0 = 2./(9.*pow(r,0.666)) * scalar K0 = 2./(9.*pow(r,0.666)) *
@ -513,44 +441,44 @@ scalar Foam::ParmarBassetForce::calculateK0(scalar r, scalar dt) const
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
scalar Foam::ParmarBassetForce::trapWeight(int i, int n) const scalar Foam::ParmarBassetForce::trapWeight(int i, int n) const
{ {
if ( (i==1) || (i==(n-1)) ) if ( (i==0) || (i==(n-1)) )
return 0.5; return 0.5;
else else
return 1.0; return 1.0;
} }
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
void Foam::ParmarBassetForce::update_ddtUrelHist(const vector& ddtUrel, int index) const void Foam::ParmarBassetForce::update_ddtUrelHist(double**& ddtUrelHist_, const vector& ddtUrel, int index) const
{ {
for (int i=0; i<3; i++) // loop over dimensions for (int i=0; i<3; i++) // loop over dimensions
{ {
for (int j=nHist_-1; j>0; j--) // loop over past times for (int j=ddtUrelHistSize_-1; j>0; j--) // loop over past times
ddtUrelHist_[j][index][i] = ddtUrelHist_[j-1][index][i]; ddtUrelHist_[index][i*ddtUrelHistSize_+j] = ddtUrelHist_[index][i*ddtUrelHistSize_+j-1];
ddtUrelHist_[0][index][i] = ddtUrel[i]; ddtUrelHist_[index][i*ddtUrelHistSize_] = ddtUrel[i];
} }
} }
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
void Foam::ParmarBassetForce::update_rHist(scalar r, int index) const void Foam::ParmarBassetForce::update_rHist(double**& rHist_, scalar r, int index) const
{ {
for (int j=nHist_-1; j>0; j--) // loop over past times for (int j=rHistSize_-1; j>0; j--) // loop over past times
rHist_[j][index][0] = rHist_[j-1][index][0]; rHist_[index][j] = rHist_[index][j-1];
rHist_[0][index][0] = r; rHist_[index][0] = r;
} }
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
void Foam::ParmarBassetForce::update_FHist(const vector& F1, const vector& F2, int index) const void Foam::ParmarBassetForce::update_FHist(double**& FHist_, const vector& F1, const vector& F2, int index) const
{ {
for (int i=0; i<3; i++) // loop over dimensions for (int i=0; i<3; i++) // loop over dimensions
{ {
for (int k=0; k<2; k++) // loop over F1, F2 for (int k=0; k<2; k++) // loop over F1, F2
for (int j=FHistSize_-1; j>0; j--) // loop over past times for (int j=FHistSize_-1; j>0; j--) // loop over past times
FHist_[k][j][index][i] = FHist_[k][j-1][index][i]; FHist_[index][i*FHistSize_*2+j*2+k] = FHist_[index][i*FHistSize_*2+(j-1)*2+k];
FHist_[0][0][index][i] = F1[i]; FHist_[index][i*FHistSize_*2 ] = F1[i];
FHist_[1][0][index][i] = F2[i]; FHist_[index][i*FHistSize_*2+1] = F2[i];
} }
} }
@ -564,18 +492,20 @@ void Foam::ParmarBassetForce::calculateCoeffs(int k, scalar t0, scalar r, double
} }
} }
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
void Foam::ParmarBassetForce::solveFlongODE(int k, double C[4], scalar dt, int index) const vector Foam::ParmarBassetForce::solveFlongODE(double**& FHist_, double**& ddtUrelHist_, int k, double C[4], scalar dt, int index) const
{ {
vector Flong = vector::zero;
if (discOrder_==1) if (discOrder_==1)
{ {
for (int i=0; i<3; i++) // loop over dimensions for (int i=0; i<3; i++) // loop over dimensions
{ {
FHist_[k][0][index][i] = Flong[i] =
( (
( C[1]/dt+2/(dt*dt)) * FHist_[k][1][index][i] ( C[1]/dt+2/(dt*dt)) * FHist_[index][i*FHistSize_*2 +k]
- ( 1/(dt*dt)) * FHist_[k][2][index][i] - ( 1/(dt*dt)) * FHist_[index][i*FHistSize_*2+2+k]
- (C[2]+C[3]/dt ) * ddtUrelHist_[nInt_ ][index][i] - (C[2]+C[3]/dt ) * ddtUrelHist_[index][i*ddtUrelHistSize_+nInt_-1]
+ ( C[3]/dt ) * ddtUrelHist_[nInt_+1][index][i] + ( C[3]/dt ) * ddtUrelHist_[index][i*ddtUrelHistSize_+nInt_ ]
) / (C[0]+C[1]/dt+1/(dt*dt)); // Eq. 3.20 using first order temporal discretisation ) / (C[0]+C[1]/dt+1/(dt*dt)); // Eq. 3.20 using first order temporal discretisation
} }
} }
@ -583,39 +513,20 @@ void Foam::ParmarBassetForce::solveFlongODE(int k, double C[4], scalar dt, int i
{ {
for (int i=0; i<3; i++) // loop over dimensions for (int i=0; i<3; i++) // loop over dimensions
{ {
FHist_[k][0][index][i] = Flong[i] =
( (
( 4*C[1]/(2*dt) + 24/(4*dt*dt)) * FHist_[k][1][index][i] ( 4*C[1]/(2*dt) + 24/(4*dt*dt)) * FHist_[index][i*FHistSize_*2 +k]
- ( C[1]/(2*dt) + 22/(4*dt*dt)) * FHist_[k][2][index][i] - ( C[1]/(2*dt) + 22/(4*dt*dt)) * FHist_[index][i*FHistSize_*2+2+k]
+ ( 8/(4*dt*dt)) * FHist_[k][3][index][i] + ( 8/(4*dt*dt)) * FHist_[index][i*FHistSize_*2+4+k]
- ( 1/(4*dt*dt)) * FHist_[k][4][index][i] - ( 1/(4*dt*dt)) * FHist_[index][i*FHistSize_*2+6+k]
- (C[2] + 3*C[3]/(2*dt) ) * ddtUrelHist_[nInt_ ][index][i] - (C[2] + 3*C[3]/(2*dt) ) * ddtUrelHist_[index][i*ddtUrelHistSize_+nInt_-1]
+ ( 4*C[3]/(2*dt) ) * ddtUrelHist_[nInt_+1][index][i] + ( 4*C[3]/(2*dt) ) * ddtUrelHist_[index][i*ddtUrelHistSize_+nInt_ ]
- ( C[3]/(2*dt) ) * ddtUrelHist_[nInt_+2][index][i] - ( C[3]/(2*dt) ) * ddtUrelHist_[index][i*ddtUrelHistSize_+nInt_+1]
) / (C[0] + 3*C[1]/(2*dt) + 9/(4*dt*dt)); // Eq. 3.20 using second order temporal discretisation ) / (C[0] + 3*C[1]/(2*dt) + 9/(4*dt*dt)); // Eq. 3.20 using second order temporal discretisation
} }
} }
} return Flong;
void Foam::ParmarBassetForce::rescaleHist(scalar tScale, scalar mScale, scalar lScale, scalar rScale, int index) const
{
for (int i=0; i<3; i++) // loop over dimensions
{
// rescale ddtU history
for (int j=0; j<nHist_; j++) // loop over past times
if (ddtUrelHist_[j][index][i] != NOTONCPU)
ddtUrelHist_[j][index][i] *= lScale/(tScale*tScale);
// rescale F1, F2 history
for (int k=0; k<2; k++) // loop over F1, F2
for (int j=0; j<FHistSize_; j++) // loop over past times
FHist_[k][j][index][i] *= mScale*lScale/(tScale*tScale);
}
// rescale r history
for (int j=0; j<nHist_; j++) // loop over past times
if (rHist_[j][index][0] != NOTONCPU)
rHist_[j][index][0] /= pow(rScale,1.5);
} }
} // End namespace Foam } // End namespace Foam

View File

@ -59,35 +59,37 @@ class ParmarBassetForce
private: private:
dictionary propsDict_; dictionary propsDict_;
word velFieldName_; const word velFieldName_;
const volVectorField& U_; const volVectorField& U_;
word UsFieldName_; const word UsFieldName_;
const volVectorField& Us_; const volVectorField& Us_;
label nInt_; //no of timesteps to solve full integral const int nInt_; //no of timesteps to solve full integral
label discOrder_; //ODE discretisation order const int discOrder_; //ODE discretisation order
label nHist_; //no of timesteps to save ddtUrel history for const int ddtUrelHistSize_; //no of timesteps to save ddtUrel history for
label FHistSize_; const int rHistSize_; //no of timesteps to save r history for
mutable List<double**> ddtUrelHist_; const int FHistSize_; //no of timesteps to save Flong history for
mutable List<double**> rHist_; const word ddtUrelHistRegName_;
mutable List<List<double**>> FHist_; const word rHistRegName_;
mutable double** gH0_; const word FHistRegName_;
mutable double** tRef_; const word gH0RegName_;
mutable double** mRef_; const word tRefRegName_;
mutable double** lRef_; const word mRefRegName_;
const word lRefRegName_;
mutable volVectorField Urel_; mutable volVectorField Urel_;
@ -101,17 +103,15 @@ private:
scalar trapWeight(int i, int n) const; scalar trapWeight(int i, int n) const;
void update_ddtUrelHist(const vector& ddtUrel, int index) const; void update_ddtUrelHist(double**& ddtUrelHist_, const vector& ddtUrel, int index) const;
void update_rHist(scalar r, int index) const; void update_rHist(double**& rHist_, scalar r, int index) const;
void update_FHist(const vector& F1, const vector& F2, int index) const; void update_FHist(double**& FHist_, const vector& F1, const vector& F2, int index) const;
void calculateCoeffs(int k, scalar t0, scalar r, double c[2][4][3], double chi[2][4][2], double C[4]) const; void calculateCoeffs(int k, scalar t0, scalar r, double c[2][4][3], double chi[2][4][2], double C[4]) const;
void solveFlongODE(int k, double C[4], scalar dt, int index) const; vector solveFlongODE(double**& FHist_, double**& ddtUrelHist_, int k, double C[4], scalar dt, int index) const;
void rescaleHist(scalar tScale, scalar mScale, scalar lScale, scalar rScale, int index) const;
public: public:
@ -136,9 +136,6 @@ public:
// Member Functions // Member Functions
void setForce() const; void setForce() const;
void reAllocArrays() const;
inline const smoothingModel& smoothingM() const inline const smoothingModel& smoothingM() const
{ {
return smoothingModel_; return smoothingModel_;

View File

@ -61,6 +61,7 @@ gradPForceSmooth::gradPForceSmooth
U_(sm.mesh().lookupObject<volVectorField> (velocityFieldName_)), U_(sm.mesh().lookupObject<volVectorField> (velocityFieldName_)),
useRho_(false), useRho_(false),
useU_(false), useU_(false),
temporalSmoothing_(false),
addedMassCoeff_(0.0), addedMassCoeff_(0.0),
smoothingModel_ smoothingModel_
( (
@ -96,7 +97,7 @@ gradPForceSmooth::gradPForceSmooth
if (modelType_ == "B") if (modelType_ == "B")
{ {
FatalError <<"using model gradPForceSmooth with model type B is not valid\n" << abort(FatalError); FatalError <<"using model gradPForceSmooth with model type B is not valid\n" << abort(FatalError);
} }
else if (modelType_ == "Bfull") else if (modelType_ == "Bfull")
{ {
@ -135,6 +136,11 @@ gradPForceSmooth::gradPForceSmooth
particleCloud_.probeM().scalarFields_.append("Vs"); particleCloud_.probeM().scalarFields_.append("Vs");
particleCloud_.probeM().scalarFields_.append("rho"); particleCloud_.probeM().scalarFields_.append("rho");
particleCloud_.probeM().writeHeader(); particleCloud_.probeM().writeHeader();
if ((smoothingM().type() == "temporalSmoothing") || (smoothingM().type() == "constDiffAndTemporalSmoothing"))
{
temporalSmoothing_ = true;
}
} }
@ -150,6 +156,11 @@ gradPForceSmooth::~gradPForceSmooth()
void gradPForceSmooth::setForce() const void gradPForceSmooth::setForce() const
{ {
volVectorField gradPField = fvc::grad(p_); volVectorField gradPField = fvc::grad(p_);
// if temporal smoothing is used, let pSmooth evolve on its own - smoothing model itself looks up p
// else, set pSmooth to current p and apply spatial smoothing
if (!temporalSmoothing_) pSmooth_ = p_;
if (pFieldName_ == "p_rgh") if (pFieldName_ == "p_rgh")
{ {
const volScalarField& rho_ = particleCloud_.mesh().lookupObject<volScalarField>("rho"); const volScalarField& rho_ = particleCloud_.mesh().lookupObject<volScalarField>("rho");

View File

@ -62,6 +62,8 @@ private:
bool useU_; // if false: substitution p=0.5*rho*U^2 bool useU_; // if false: substitution p=0.5*rho*U^2
bool temporalSmoothing_;
mutable double addedMassCoeff_; //added mass coefficient mutable double addedMassCoeff_; //added mass coefficient
autoPtr<smoothingModel> smoothingModel_; autoPtr<smoothingModel> smoothingModel_;

View File

@ -0,0 +1,129 @@
/*---------------------------------------------------------------------------*\
License
This 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.
This code 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 this code. If not, see <http://www.gnu.org/licenses/>.
Copyright (C) 2015- Thomas Lichtenegger, JKU Linz, Austria
Description
transfer fluid properties to LIGGGHTS
SourceFiles
transferFluidProperties.C
\*---------------------------------------------------------------------------*/
#include "error.H"
#include "transferFluidProperties.H"
#include "addToRunTimeSelectionTable.H"
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
namespace Foam
{
// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
defineTypeNameAndDebug(transferFluidProperties, 0);
addToRunTimeSelectionTable
(
forceModel,
transferFluidProperties,
dictionary
);
// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
// Construct from components
transferFluidProperties::transferFluidProperties
(
const dictionary& dict,
cfdemCloud& sm
)
:
forceModel(dict,sm),
propsDict_(dict.subDict(typeName + "Props"))
{
particleCloud_.registerParticleProperty<double**>("fluidDensity",1);
particleCloud_.registerParticleProperty<double**>("fluidViscosity",1);
// init force sub model
setForceSubModels(propsDict_);
// define switches which can be read from dict
forceSubM(0).setSwitchesList(SW_VERBOSE,true); // activate search for verbose switch
forceSubM(0).setSwitchesList(SW_INTERPOLATION,true); // activate search for interpolate switch
forceSubM(0).readSwitches();
}
// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * //
transferFluidProperties::~transferFluidProperties()
{
}
// * * * * * * * * * * * * * * * private Member Functions * * * * * * * * * * * * * //
// * * * * * * * * * * * * * * * public Member Functions * * * * * * * * * * * * * //
void transferFluidProperties::setForce() const
{
double**& fluidDensity_ = particleCloud_.getParticlePropertyRef<double**>("fluidDensity");
double**& fluidViscosity_ = particleCloud_.getParticlePropertyRef<double**>("fluidViscosity");
const volScalarField& rhoField = forceSubM(0).rhoField();
const volScalarField& nufField = forceSubM(0).nuField();
interpolationCellPoint<scalar> rhoInterpolator_(rhoField);
interpolationCellPoint<scalar> nufInterpolator_(nufField);
label cellI = 0;
double rho = 0.;
double nuf = 0.;
vector position(0,0,0);
for(int index = 0; index < particleCloud_.numberOfParticles(); ++index)
{
cellI = particleCloud_.cellIDs()[index][0];
if (cellI >= 0)
{
if(forceSubM(0).interpolation())
{
position = particleCloud_.position(index);
rho = rhoInterpolator_.interpolate(position,cellI);
nuf = nufInterpolator_.interpolate(position,cellI);
}
else
{
rho = rhoField[cellI];
nuf = nufField[cellI];
}
fluidDensity_[index][0] = rho;
fluidViscosity_[index][0] = nuf*rho;
}
}
particleCloud_.dataExchangeM().giveData("fluidDensity","scalar-atom",fluidDensity_);
particleCloud_.dataExchangeM().giveData("fluidViscosity","scalar-atom",fluidViscosity_);
if (forceSubM(0).verbose()) Info << "give data done" << endl;
}
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
} // End namespace Foam
// ************************************************************************* //

View File

@ -0,0 +1,79 @@
/*---------------------------------------------------------------------------*\
License
This 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.
This code 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 this code. If not, see <http://www.gnu.org/licenses/>.
Copyright (C) 2015- Thomas Lichtenegger, JKU Linz, Austria
Description
transfer fluid properties to LIGGGHTS
SourceFiles
transferFluidProperties.C
\*---------------------------------------------------------------------------*/
#ifndef transferFluidProperties_H
#define transferFluidProperties_H
#include "forceModel.H"
#include "interpolationCellPoint.H"
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
namespace Foam
{
/*---------------------------------------------------------------------------*\
Class transferFluidProperties Declaration
\*---------------------------------------------------------------------------*/
class transferFluidProperties
:
public forceModel
{
private:
dictionary propsDict_;
public:
//- Runtime type information
TypeName("transferFluidProperties");
// Constructors
//- Construct from components
transferFluidProperties
(
const dictionary& dict,
cfdemCloud& sm
);
// Destructor
~transferFluidProperties();
// Member Functions
void setForce() const;
};
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
} // End namespace Foam
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
#endif
// ************************************************************************* //

View File

@ -99,7 +99,12 @@ virtualMassForce::virtualMassForce
) )
) )
{ {
particleCloud_.registerParticleProperty<double**>(UrelOldRegName_,3,NOTONCPU,false); // allocate UrelOld only if needed
int UrelOldSize = 0;
if(!splitUrelCalculation_ || !useUs_ )
UrelOldSize = 3;
particleCloud_.registerParticleProperty<double**>(UrelOldRegName_,UrelOldSize,NOTONCPU,false);
// init force sub model // init force sub model
setForceSubModels(propsDict_); setForceSubModels(propsDict_);

View File

@ -105,8 +105,6 @@ public:
virtual void postFlow() {} virtual void postFlow() {}
virtual void solve() {}
const volScalarField& D0Field() const; const volScalarField& D0Field() const;
const volScalarField& CsField() const; const volScalarField& CsField() const;

View File

@ -219,7 +219,7 @@ void particleProbe::writeProbe(int index, Field<scalar> sValues, Field<vector> v
*sPtr << setprecision(writePrecision_); *sPtr << setprecision(writePrecision_);
forAll(vValues, iter) forAll(vValues, iter)
{ {
// if(!probeDebug_ && iter>0) break; if(!probeDebug_ && iter>0) break;
*sPtr << vValues[iter][0] << " "; *sPtr << vValues[iter][0] << " ";
*sPtr << vValues[iter][1] << " "; *sPtr << vValues[iter][1] << " ";
*sPtr << vValues[iter][2] << " "; *sPtr << vValues[iter][2] << " ";

View File

@ -68,6 +68,7 @@ constDiffAndTemporalSmoothing::constDiffAndTemporalSmoothing
smoothingLength_(dimensionedScalar("smoothingLength",dimensionSet(0,1,0,0,0,0,0), readScalar(propsDict_.lookup("smoothingLength")))), smoothingLength_(dimensionedScalar("smoothingLength",dimensionSet(0,1,0,0,0,0,0), readScalar(propsDict_.lookup("smoothingLength")))),
smoothingLengthReferenceField_(dimensionedScalar("smoothingLengthReferenceField",dimensionSet(0,1,0,0,0,0,0), readScalar(propsDict_.lookup("smoothingLength")))), smoothingLengthReferenceField_(dimensionedScalar("smoothingLengthReferenceField",dimensionSet(0,1,0,0,0,0,0), readScalar(propsDict_.lookup("smoothingLength")))),
DT_("DT", dimensionSet(0,2,-1,0,0), 0.), DT_("DT", dimensionSet(0,2,-1,0,0), 0.),
refFieldName_(propsDict_.lookupOrDefault<word>("refField","")),
gamma_(readScalar(propsDict_.lookup("smoothingStrength"))), gamma_(readScalar(propsDict_.lookup("smoothingStrength"))),
correctBoundary_(propsDict_.lookupOrDefault<bool>("correctBoundary",false)), correctBoundary_(propsDict_.lookupOrDefault<bool>("correctBoundary",false)),
verbose_(false) verbose_(false)
@ -111,12 +112,43 @@ void constDiffAndTemporalSmoothing::smoothen(volScalarField& fieldSrc) const
double deltaT = sSmoothField.mesh().time().deltaTValue(); double deltaT = sSmoothField.mesh().time().deltaTValue();
DT_.value() = smoothingLength_.value() * smoothingLength_.value() / deltaT; DT_.value() = smoothingLength_.value() * smoothingLength_.value() / deltaT;
// do smoothing if(refFieldName_.empty())
solve {
( // do spatial smoothing
fvm::ddt(sSmoothField) solve
-fvm::laplacian(DT_, sSmoothField) (
); fvm::ddt(sSmoothField)
-fvm::laplacian(DT_, sSmoothField)
);
// create fields for temporal smoothing
volScalarField refField = sSmoothField;
sSmoothField.ref()=fieldSrc.oldTime().internalField();
sSmoothField.correctBoundaryConditions();
sSmoothField.oldTime()=fieldSrc.oldTime();
sSmoothField.oldTime().correctBoundaryConditions();
// do temporal smoothing
solve
(
fvm::ddt(sSmoothField)
-
gamma_/deltaT * (refField - fvm::Sp(1.0,sSmoothField))
);
}
else
{
const volScalarField& refField = particleCloud_.mesh().lookupObject<volScalarField>(refFieldName_);
// do spatial and temporal smoothing
solve
(
fvm::ddt(sSmoothField)
-fvm::laplacian(DT_, sSmoothField)
-gamma_/deltaT * (refField - fvm::Sp(1.0,sSmoothField))
);
}
// bound sSmoothField_ // bound sSmoothField_
forAll(sSmoothField,cellI) forAll(sSmoothField,cellI)
@ -152,28 +184,43 @@ void constDiffAndTemporalSmoothing::smoothen(volVectorField& fieldSrc) const
dimensionedScalar deltaT = vSmoothField.mesh().time().deltaT(); dimensionedScalar deltaT = vSmoothField.mesh().time().deltaT();
DT_.value() = smoothingLength_.value() * smoothingLength_.value() / deltaT.value(); DT_.value() = smoothingLength_.value() * smoothingLength_.value() / deltaT.value();
// do spacial smoothing if(refFieldName_.empty())
solve {
( // do spatial smoothing
fvm::ddt(vSmoothField) solve
-fvm::laplacian(DT_, vSmoothField) (
); fvm::ddt(vSmoothField)
-fvm::laplacian(DT_, vSmoothField)
);
// create fields for temporal smoothing // create fields for temporal smoothing
volVectorField refField = vSmoothField; volVectorField refField = vSmoothField;
vSmoothField.ref()=fieldSrc.oldTime().internalField(); vSmoothField.ref()=fieldSrc.oldTime().internalField();
vSmoothField.correctBoundaryConditions(); vSmoothField.correctBoundaryConditions();
vSmoothField.oldTime()=fieldSrc.oldTime(); vSmoothField.oldTime()=fieldSrc.oldTime();
vSmoothField.oldTime().correctBoundaryConditions(); vSmoothField.oldTime().correctBoundaryConditions();
// do temporal smoothing // do temporal smoothing
solve solve
( (
fvm::ddt(vSmoothField) fvm::ddt(vSmoothField)
- -
gamma_/deltaT * (refField - fvm::Sp(1.0,vSmoothField)) gamma_/deltaT * (refField - fvm::Sp(1.0,vSmoothField))
); );
}
else
{
const volVectorField& refField = particleCloud_.mesh().lookupObject<volVectorField>(refFieldName_);
// do spatial and temporal smoothing
solve
(
fvm::ddt(vSmoothField)
-fvm::laplacian(DT_, vSmoothField)
-gamma_/deltaT * (refField - fvm::Sp(1.0,vSmoothField))
);
}
// create temporally smoothened boundary field // create temporally smoothened boundary field
if (correctBoundary_) if (correctBoundary_)

View File

@ -6,7 +6,7 @@
Christoph Goniva, christoph.goniva@cfdem.com Christoph Goniva, christoph.goniva@cfdem.com
Copyright 2009-2012 JKU Linz Copyright 2009-2012 JKU Linz
Copyright 2012- DCS Computing GmbH, Linz Copyright 2012- DCS Computing GmbH, Linz
Copyright (C) 2013- Graz University of Copyright (C) 2013- Graz University of
Technology, IPPT Technology, IPPT
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
@ -65,6 +65,7 @@ private:
dimensionedScalar smoothingLength_; dimensionedScalar smoothingLength_;
dimensionedScalar smoothingLengthReferenceField_; dimensionedScalar smoothingLengthReferenceField_;
mutable dimensionedScalar DT_; mutable dimensionedScalar DT_;
word refFieldName_;
scalar gamma_; scalar gamma_;
bool correctBoundary_; bool correctBoundary_;
bool verbose_; bool verbose_;
@ -93,7 +94,7 @@ public:
bool doSmoothing() const; bool doSmoothing() const;
//void dSmoothing(volScalarField&) const; //void dSmoothing(volScalarField&) const;
void smoothen(volScalarField&) const; void smoothen(volScalarField&) const;
void smoothen(volVectorField&) const; void smoothen(volVectorField&) const;

View File

@ -130,7 +130,7 @@ void Foam::temporalSmoothing::smoothen(volVectorField& fieldSrc) const
vSmoothField.oldTime()=fieldSrc; vSmoothField.oldTime()=fieldSrc;
vSmoothField.oldTime().correctBoundaryConditions(); vSmoothField.oldTime().correctBoundaryConditions();
volVectorField refField = particleCloud_.mesh().lookupObject<volVectorField>(refFieldName_); const volVectorField& refField = particleCloud_.mesh().lookupObject<volVectorField>(refFieldName_);
dimensionedScalar deltaT = vSmoothField.mesh().time().deltaT(); dimensionedScalar deltaT = vSmoothField.mesh().time().deltaT();
solve solve

View File

@ -90,6 +90,7 @@ $(forceModels)/directedDiffusiveRelaxation/directedDiffusiveRelaxation.C
$(forceModels)/BeetstraDrag/BeetstraDrag.C $(forceModels)/BeetstraDrag/BeetstraDrag.C
$(forceModels)/BeetstraDragPoly/BeetstraDragPoly.C $(forceModels)/BeetstraDragPoly/BeetstraDragPoly.C
$(forceModels)/dSauter/dSauter.C $(forceModels)/dSauter/dSauter.C
$(forceModels)/transferFluidProperties/transferFluidProperties.C
$(forceModels)/Fines/Fines.C $(forceModels)/Fines/Fines.C
$(forceModels)/Fines/FinesFields.C $(forceModels)/Fines/FinesFields.C
$(forceModels)/Fines/FanningDynFines.C $(forceModels)/Fines/FanningDynFines.C

View File

@ -159,7 +159,24 @@ standardRecModel::standardRecModel
// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * //
standardRecModel::~standardRecModel() standardRecModel::~standardRecModel()
{} {
const objectRegistry& objReg = base_.mesh().thisDb();
for(int j=0; j<volScalarFieldNames_.size(); j++)
{
objReg.checkOut(volScalarFieldList_[j][virtualTimeIndex]);
}
for(int j=0; j<volVectorFieldNames_.size(); j++)
{
objReg.checkOut(volVectorFieldList_[j][virtualTimeIndex]);
}
for(int j=0; j<surfaceScalarFieldNames_.size(); j++)
{
objReg.checkOut(surfaceScalarFieldList_[j][virtualTimeIndex]);
}
}
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //

View File

@ -1,33 +1,39 @@
clear all; clear all;
clc; clc;
%% Script to plot the angular velocities and the particle positions % plot the angular velocity and the particle position
A = importdata('../../DEM/post/angular_velocity_no_coupling.txt',' ',1); A = importdata('../../DEM/post/angular_velocity.txt',' ',1);
B = importdata('../../DEM/post/position_no_coupling.txt',' ',1); B = importdata('../../DEM/post/position.txt',' ',1);
C = importdata('../../DEM/post/angular_velocity.txt',' ',1);
D = importdata('../../DEM/post/position.txt',' ',1);
pos1 = B.data(); omega = A.data();
omega1 = A.data(); pos = B.data();
pos2 = D.data();
omega2 = C.data();
time = omega1(:,1); time1 = omega(:,1);
omegax1 = omega1(:,2); omegax = omega(:,2);
omegay1 = omega1(:,3); omegay = omega(:,3);
omegaz1 = omega1(:,4); omegaz = omega(:,4);
time2 = omega2(:,1); time2 = pos(:,1);
omegax2 = omega2(:,2); posx = pos(:,2);
omegay2 = omega2(:,3); posy = pos(:,3);
omegaz2 = omega2(:,4); posz = pos(:,4);
figure figure(1)
plot(time,omegaz1,'-.-',time2,omegaz2,'Linewidth',1.5) plot(time1,omegaz,'-.-','Linewidth',1.5)
xlabel('Time (s)') xlabel('Time (s)')
ylabel('Angular velocity (1/s)') ylabel('Angular velocity (1/s)')
legend('One-way coupling','Two-way coupling') legend('Two-way torque coupling')
axis([0 0.5 0 11]) axis([0 0.5 0 11])
set(gca,'FontSize',12) set(gca,'FontSize',12)
print('angular_velocity_compare.eps') print('angular_velocity.eps')
figure(2)
plot(time2,posy,'-.-','Linewidth',1.5)
xlabel('Time (s)')
ylabel('Y-position (m)')
legend('Two-way torque coupling')
axis([0 0.5 0 0.1])
set(gca,'FontSize',12)
print('position.eps')

View File

@ -0,0 +1,21 @@
{
"type" : "CFDEMcoupling",
"runs" : [
{
"name" : "cfdemrun",
"solver" : "cfdemSolverIB",
"type" : "CFDEMcoupling/mpi",
"nprocs" : 4,
"data" : {
"series" : [
{"name" : "angular_velocity", "file" : "angular_velocity.txt", "columns" : ["t", "omegax", "omegay", "omegaz"]},
{"name" : "position", "file" : "position.txt", "columns" : ["t", "x", "y", "z"]}
],
"plots" : [
{"name" : "z-omega", "title" : "Particle z-Angular Velocity", "xdata" : "angular_velocity.t", "ydata" : ["angular_velocity.omegaz"], "xlabel" : "time [s]", "ylabel" : "angular velocity [1/s]"},
{"name" : "y-position", "title" : "Particle y-Position", "xdata" : "position.t", "ydata" : ["position.y"], "xlabel" : "time [s]", "ylabel" : "position [m]"}
]
}
}
]
}

View File

@ -45,7 +45,7 @@ plt.xlabel('Time (s)')
plt.ylabel('Min. eigen value of G') plt.ylabel('Min. eigen value of G')
plt.minorticks_on() plt.minorticks_on()
plt.grid() plt.grid()
plt.savefig('RBC_Posieuille_Gyration.eps') plt.savefig('RBC_Poiseuille_Gyration.eps')
plt.show() plt.show()

View File

@ -0,0 +1,27 @@
{
"type" : "CFDEMcoupling",
"runs" : [
{
"name" : "liggghts-init",
"input_script" : "DEM/in.liggghts_init",
"type" : "liggghts/serial"
},
{
"name" : "cfdemrun",
"depends_on" : "liggghts-init",
"solver" : "cfdemSolverIBContinuousForcing",
"type" : "CFDEMcoupling/mpi",
"nprocs" : 2,
"data" : {
"series" : [
{"name" : "position", "file" : "particle_position.txt", "columns" : ["t", "x1", "y1", "z1", "x2", "y2", "z2", "x3", "y3", "z3", "x4", "y4", "z4", "x5", "y5", "z5", "x6", "y6", "z6", "x7", "y7", "z7", "x8", "y8", "z8", "x9", "y9", "z9", "x10", "y10", "z10"]}
],
"plots" : [
{"name" : "x-position", "title" : "Particle x-Position", "xdata" : "position.t", "ydata" : ["position.x1","position.x2","position.x3","position.x4","position.x5","position.x6","position.x7","position.x8","position.x9","position.x10"], "xlabel" : "time [1e-6 s]", "ylabel" : "position [1e-6 m]"},
{"name" : "y-position", "title" : "Particle y-Position", "xdata" : "position.t", "ydata" : ["position.y1","position.y2","position.y3","position.y4","position.y5","position.y6","position.y7","position.y8","position.y9","position.y10"], "xlabel" : "time [1e-6 s]", "ylabel" : "position [1e-6 m]"},
{"name" : "z-position", "title" : "Particle z-Position", "xdata" : "position.t", "ydata" : ["position.z1","position.z2","position.z3","position.z4","position.z5","position.z6","position.z7","position.z8","position.z9","position.z10"], "xlabel" : "time [1e-6 s]", "ylabel" : "position [1e-6 m]"}
]
}
}
]
}

View File

@ -0,0 +1,27 @@
{
"type" : "CFDEMcoupling",
"runs" : [
{
"name" : "liggghts-init",
"input_script" : "DEM/in.liggghts_init",
"type" : "liggghts/serial"
},
{
"name" : "cfdemrun",
"depends_on" : "liggghts-init",
"solver" : "cfdemSolverIBContinuousForcing",
"type" : "CFDEMcoupling/mpi",
"nprocs" : 2,
"data" : {
"series" : [
{"name" : "position", "file" : "particle_position.txt", "columns" : ["t", "x1", "y1", "z1", "x2", "y2", "z2", "x3", "y3", "z3", "x4", "y4", "z4", "x5", "y5", "z5", "x6", "y6", "z6", "x7", "y7", "z7", "x8", "y8", "z8", "x9", "y9", "z9", "x10", "y10", "z10"]}
],
"plots" : [
{"name" : "x-position", "title" : "Particle x-Position", "xdata" : "position.t", "ydata" : ["position.x1","position.x2","position.x3","position.x4","position.x5","position.x6","position.x7","position.x8","position.x9","position.x10"], "xlabel" : "time [1e-6 s]", "ylabel" : "position [1e-6 m]"},
{"name" : "y-position", "title" : "Particle y-Position", "xdata" : "position.t", "ydata" : ["position.y1","position.y2","position.y3","position.y4","position.y5","position.y6","position.y7","position.y8","position.y9","position.y10"], "xlabel" : "time [1e-6 s]", "ylabel" : "position [1e-6 m]"},
{"name" : "z-position", "title" : "Particle z-Position", "xdata" : "position.t", "ydata" : ["position.z1","position.z2","position.z3","position.z4","position.z5","position.z6","position.z7","position.z8","position.z9","position.z10"], "xlabel" : "time [1e-6 s]", "ylabel" : "position [1e-6 m]"}
]
}
}
]
}

View File

@ -173,6 +173,9 @@ FinesFieldsProps
poresizeWidth 0.2; poresizeWidth 0.2;
verbose true; verbose true;
diffCoeff 0.005; diffCoeff 0.005;
tauRelease 0.1;
depositionLength 0.1;
kineticClogging true;
} }
gravityProps gravityProps

View File

@ -23,13 +23,13 @@ startTime 0;
stopAt endTime; stopAt endTime;
endTime 40; endTime 10;
deltaT 0.0005; deltaT 0.0005;
writeControl timeStep; writeControl timeStep;
writeInterval 8000; writeInterval 1000;
purgeWrite 0; purgeWrite 0;

View File

@ -2,3 +2,4 @@ cd CFD
blockMesh blockMesh
topoSet -dict system/topoSetDict topoSet -dict system/topoSetDict
cp -r orig.0/ 0 cp -r orig.0/ 0
decomposePar

View File

@ -77,11 +77,11 @@ fix cfd5 ore chem/shrink/core speciesA CO molMassA 0.02801 speciesC CO2 molM
fix cfd6 ore chem/shrink/core speciesA H2 molMassA 0.00202 speciesC H2O molMassC 0.01801 scale_reduction_rate ${rate_scale} fix cfd6 ore chem/shrink/core speciesA H2 molMassA 0.00202 speciesC H2O molMassC 0.01801 scale_reduction_rate ${rate_scale}
# material properties for chemical reaction # material properties for chemical reaction
fix k0_CO ore property/atom k0_cfd5 vector yes no no 17 25 2700 fix k0_CO ore property/global k0_cfd5 vector 17 25 2700
fix Ea_CO ore property/atom Ea_cfd5 vector yes no no 69488 95000 130940 fix Ea_CO ore property/global Ea_cfd5 vector 69488 95000 130940
fix k0_H2 ore property/atom k0_cfd6 vector yes no no 30 23 160 fix k0_H2 ore property/global k0_cfd6 vector 30 23 160
fix Ea_H2 ore property/atom Ea_cfd6 vector yes no no 63627 85000 105908 fix Ea_H2 ore property/global Ea_cfd6 vector 63627 85000 105908
# particle parameters # particle parameters
fix porosity ore property/global porosity_ore vector 0.61 0.34 0.19 0.17 fix porosity ore property/global porosity_ore vector 0.61 0.34 0.19 0.17

View File

@ -62,11 +62,11 @@ fix cfd5 all chem/shrink/core speciesA CO molMassA 0.02801 speciesC CO2 molM
fix cfd6 all chem/shrink/core speciesA H2 molMassA 0.00202 speciesC H2O molMassC 0.01801 scale_reduction_rate 10.0 screen yes fix cfd6 all chem/shrink/core speciesA H2 molMassA 0.00202 speciesC H2O molMassC 0.01801 scale_reduction_rate 10.0 screen yes
# Chemical properties for unreacted shrink core (activate only when chem/shrink/core is active) # Chemical properties for unreacted shrink core (activate only when chem/shrink/core is active)
fix k0_CO all property/atom k0_cfd5 vector yes no no 17 25 2700 fix k0_CO all property/global k0_cfd5 vector 17 25 2700
fix Ea_CO all property/atom Ea_cfd5 vector yes no no 69488 73674 113859 fix Ea_CO all property/global Ea_cfd5 vector 69488 73674 113859
fix k0_H2 all property/atom k0_cfd6 vector yes no no 30 23 160 fix k0_H2 all property/global k0_cfd6 vector 30 23 160
fix Ea_H2 all property/atom Ea_cfd6 vector yes no no 63627 71162 92092 fix Ea_H2 all property/global Ea_cfd6 vector 63627 71162 92092
# particle porosity/tortuosity/pore diameter # particle porosity/tortuosity/pore diameter
fix porosity all property/global porosity_all vector 0.65 0.31 0.16 0.15 fix porosity all property/global porosity_all vector 0.65 0.31 0.16 0.15
@ -95,20 +95,6 @@ variable ke_tot equal c_KinEn
# print total kinetic energy # print total kinetic energy
fix printCompute all print ${WI} "${time} ${ke_tot}" file ../DEM/post/printKE.txt title "#time ke_tot" fix printCompute all print ${WI} "${time} ${ke_tot}" file ../DEM/post/printKE.txt title "#time ke_tot"
compute Ea_CO all reduce sum f_Ea_CO[1] f_Ea_CO[2] f_Ea_CO[3]
fix Ea all ave/time 1 1 1 c_Ea_CO[1] c_Ea_CO[2] c_Ea_CO[3]
variable Ea1 equal f_Ea[1]
variable Ea2 equal f_Ea[2]
variable Ea3 equal f_Ea[3]
compute k0CO all reduce sum f_k0_CO[1] f_k0_CO[2] f_k0_CO[3]
fix k0 all ave/time 1 1 1 c_k0CO[1] c_k0CO[2] c_k0CO[3]
variable k01 equal f_k0[1]
variable k02 equal f_k0[2]
variable k03 equal f_k0[3]
fix printk0Ea all print ${WI} "${time} ${Ea1} ${Ea2} ${Ea3} ${k01} ${k02} ${k03}" file ../DEM/post/k0Ea.dat title "#time Ea1 Ea2 Ea3 k01 k02 k03"
############### ###############
# Print out values affecting chemical reduction into specified folder for given time # Print out values affecting chemical reduction into specified folder for given time
# Diffusion Coefficient for CO and H2 # Diffusion Coefficient for CO and H2

View File

@ -62,11 +62,11 @@ fix cfd5 all chem/shrink/core speciesA CO molMassA 0.02801 speciesC CO2 molM
fix cfd6 all chem/shrink/core speciesA H2 molMassA 0.00202 speciesC H2O molMassC 0.01801 scale_reduction_rate 10.0 screen yes fix cfd6 all chem/shrink/core speciesA H2 molMassA 0.00202 speciesC H2O molMassC 0.01801 scale_reduction_rate 10.0 screen yes
# Chemical properties for unreacted shrink core (activate only when chem/shrink/core is active) # Chemical properties for unreacted shrink core (activate only when chem/shrink/core is active)
fix k0_CO all property/atom k0_cfd5 vector yes no no 17 25 2700 fix k0_CO all property/global k0_cfd5 vector 17 25 2700
fix Ea_CO all property/atom Ea_cfd5 vector yes no no 69488 73674 113859 fix Ea_CO all property/global Ea_cfd5 vector 69488 73674 113859
fix k0_H2 all property/atom k0_cfd6 vector yes no no 30 23 160 fix k0_H2 all property/global k0_cfd6 vector 30 23 160
fix Ea_H2 all property/atom Ea_cfd6 vector yes no no 63627 71162 92092 fix Ea_H2 all property/global Ea_cfd6 vector 63627 71162 92092
# particle porosity/tortuosity/pore diameter # particle porosity/tortuosity/pore diameter
fix porosity all property/global porosity_all vector 0.65 0.31 0.16 0.15 fix porosity all property/global porosity_all vector 0.65 0.31 0.16 0.15
@ -95,20 +95,6 @@ variable ke_tot equal c_KinEn
# print total kinetic energy # print total kinetic energy
fix printCompute all print ${WI} "${time} ${ke_tot}" file ../DEM/post/printKE.txt title "#time ke_tot" fix printCompute all print ${WI} "${time} ${ke_tot}" file ../DEM/post/printKE.txt title "#time ke_tot"
compute Ea_CO all reduce sum f_Ea_CO[1] f_Ea_CO[2] f_Ea_CO[3]
fix Ea all ave/time 1 1 1 c_Ea_CO[1] c_Ea_CO[2] c_Ea_CO[3]
variable Ea1 equal f_Ea[1]
variable Ea2 equal f_Ea[2]
variable Ea3 equal f_Ea[3]
compute k0CO all reduce sum f_k0_CO[1] f_k0_CO[2] f_k0_CO[3]
fix k0 all ave/time 1 1 1 c_k0CO[1] c_k0CO[2] c_k0CO[3]
variable k01 equal f_k0[1]
variable k02 equal f_k0[2]
variable k03 equal f_k0[3]
fix printk0Ea all print ${WI} "${time} ${Ea1} ${Ea2} ${Ea3} ${k01} ${k02} ${k03}" file ../DEM/post/k0Ea.dat title "#time Ea1 Ea2 Ea3 k01 k02 k03"
############### ###############
# Print out values affecting chemical reduction into specified folder for given time # Print out values affecting chemical reduction into specified folder for given time
# Diffusion Coefficient for CO and H2 # Diffusion Coefficient for CO and H2

View File

@ -61,8 +61,8 @@ fix cfd3 all couple/cfd/chemistry n_species 3 species_names CO CO2 N2 n_diff
fix cfd5 all chem/shrink/core speciesA CO molMassA 0.02801 speciesC CO2 molMassC 0.04401 scale_reduction_rate 10.0 screen yes fix cfd5 all chem/shrink/core speciesA CO molMassA 0.02801 speciesC CO2 molMassC 0.04401 scale_reduction_rate 10.0 screen yes
# Chemical properties for unreacted shrink core (activate only when chem/shrink/core is active) # Chemical properties for unreacted shrink core (activate only when chem/shrink/core is active)
fix k0_CO all property/atom k0_cfd5 vector yes no no 17 25 2700 fix k0_CO all property/global k0_cfd5 vector 17 25 2700
fix Ea_CO all property/atom Ea_cfd5 vector yes no no 69488 73674 113859 fix Ea_CO all property/global Ea_cfd5 vector 69488 73674 113859
# particle porosity/tortuosity/pore diameter # particle porosity/tortuosity/pore diameter
fix porosity all property/global porosity_all vector 0.65 0.31 0.16 0.15 fix porosity all property/global porosity_all vector 0.65 0.31 0.16 0.15
@ -91,20 +91,6 @@ variable ke_tot equal c_KinEn
# print total kinetic energy # print total kinetic energy
fix printCompute all print ${WI} "${time} ${ke_tot}" file ../DEM/post/printKE.txt title "#time ke_tot" fix printCompute all print ${WI} "${time} ${ke_tot}" file ../DEM/post/printKE.txt title "#time ke_tot"
compute Ea_CO all reduce sum f_Ea_CO[1] f_Ea_CO[2] f_Ea_CO[3]
fix Ea all ave/time 1 1 1 c_Ea_CO[1] c_Ea_CO[2] c_Ea_CO[3]
variable Ea1 equal f_Ea[1]
variable Ea2 equal f_Ea[2]
variable Ea3 equal f_Ea[3]
compute k0CO all reduce sum f_k0_CO[1] f_k0_CO[2] f_k0_CO[3]
fix k0 all ave/time 1 1 1 c_k0CO[1] c_k0CO[2] c_k0CO[3]
variable k01 equal f_k0[1]
variable k02 equal f_k0[2]
variable k03 equal f_k0[3]
fix printk0Ea all print ${WI} "${time} ${Ea1} ${Ea2} ${Ea3} ${k01} ${k02} ${k03}" file ../DEM/post/k0Ea.dat title "#time Ea1 Ea2 Ea3 k01 k02 k03"
############### ###############
# Print out values affecting chemical reduction into specified folder for given time # Print out values affecting chemical reduction into specified folder for given time
# Diffusion Coefficient for CO and H2 # Diffusion Coefficient for CO and H2

View File

@ -61,8 +61,8 @@ fix cfd3 all couple/cfd/chemistry n_species 3 species_names CO CO2 N2 n_diff
fix cfd5 all chem/shrink/core speciesA CO molMassA 0.02801 speciesC CO2 molMassC 0.04401 scale_reduction_rate 10.0 screen yes fix cfd5 all chem/shrink/core speciesA CO molMassA 0.02801 speciesC CO2 molMassC 0.04401 scale_reduction_rate 10.0 screen yes
# Chemical properties for unreacted shrink core (activate only when chem/shrink/core is active) # Chemical properties for unreacted shrink core (activate only when chem/shrink/core is active)
fix k0_CO all property/atom k0_cfd5 vector yes no no 17 25 2700 fix k0_CO all property/global k0_cfd5 vector 17 25 2700
fix Ea_CO all property/atom Ea_cfd5 vector yes no no 69488 73674 113859 fix Ea_CO all property/global Ea_cfd5 vector 69488 73674 113859
# particle porosity/tortuosity/pore diameter # particle porosity/tortuosity/pore diameter
fix porosity all property/global porosity_all vector 0.65 0.31 0.16 0.15 fix porosity all property/global porosity_all vector 0.65 0.31 0.16 0.15
@ -91,20 +91,6 @@ variable ke_tot equal c_KinEn
# print total kinetic energy # print total kinetic energy
fix printCompute all print ${WI} "${time} ${ke_tot}" file ../DEM/post/printKE.txt title "#time ke_tot" fix printCompute all print ${WI} "${time} ${ke_tot}" file ../DEM/post/printKE.txt title "#time ke_tot"
compute Ea_CO all reduce sum f_Ea_CO[1] f_Ea_CO[2] f_Ea_CO[3]
fix Ea all ave/time 1 1 1 c_Ea_CO[1] c_Ea_CO[2] c_Ea_CO[3]
variable Ea1 equal f_Ea[1]
variable Ea2 equal f_Ea[2]
variable Ea3 equal f_Ea[3]
compute k0CO all reduce sum f_k0_CO[1] f_k0_CO[2] f_k0_CO[3]
fix k0 all ave/time 1 1 1 c_k0CO[1] c_k0CO[2] c_k0CO[3]
variable k01 equal f_k0[1]
variable k02 equal f_k0[2]
variable k03 equal f_k0[3]
fix printk0Ea all print ${WI} "${time} ${Ea1} ${Ea2} ${Ea3} ${k01} ${k02} ${k03}" file ../DEM/post/k0Ea.dat title "#time Ea1 Ea2 Ea3 k01 k02 k03"
############### ###############
# Print out values affecting chemical reduction into specified folder for given time # Print out values affecting chemical reduction into specified folder for given time
# Diffusion Coefficient for CO and H2 # Diffusion Coefficient for CO and H2

View File

@ -31,6 +31,14 @@ dumpIndexDisplacementIncrement 8000;
dumpIndexInputIncrement 4000; dumpIndexInputIncrement 4000;
posIndex 0;
posX 1;
posY 2;
posZ 3;
nNeighMin 3; nNeighMin 3;
timePerDisplacementStep 0.1; timePerDisplacementStep 0.1;

View File

@ -52,7 +52,7 @@ surfaceScalarFields
//verbose true; //verbose true;
couplingSubStep 3; couplingSubStep 7;
initialRecSteps 150; initialRecSteps 150;

View File

@ -1,49 +0,0 @@
/*--------------------------------*- C++ -*----------------------------------*\
| ========= | |
| \\ / F ield | OpenFOAM: The Open Source CFD Toolbox |
| \\ / O peration | Version: 2.3.0 |
| \\ / A nd | Web: www.OpenFOAM.org |
| \\/ M anipulation | |
\*---------------------------------------------------------------------------*/
FoamFile
{
version 2.0;
format ascii;
class dictionary;
location "constant";
object thermophysicalProperties;
}
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
thermoType
{
type hePsiThermo;
mixture pureMixture;
transport const;
thermo eConst;
equationOfState perfectGas;
specie specie;
energy sensibleInternalEnergy;
}
mixture
{
specie
{
nMoles 1;
molWeight 42.1;
}
thermodynamics
{
Cv 1310;
Hf 0;
}
transport
{
mu 1e-05;
Pr 0.72;
}
}
// ************************************************************************* //

View File

@ -27,4 +27,8 @@ Cv Cv [ 0 2 -2 -1 0 0 0 ] 1310;
molM molM [1 0 0 0 -1 0 0 ] 0.0421; molM molM [1 0 0 0 -1 0 0 ] 0.0421;
TMax TMax [0 0 0 1 0 0 0] 400;
TMin TMin [0 0 0 1 0 0 0] 250;
// ************************************************************************* // // ************************************************************************* //

File diff suppressed because it is too large Load Diff

View File

@ -51,6 +51,63 @@ libs (
functions functions
{ {
Tave
{
type volFieldValue;
libs ("libfieldFunctionObjects.so");
log true;
writeControl timeStep;
writeInterval 10;
writeFields false;
regionType all;
operation volAverage;
weightField voidfractionRec;
fields
(
T
);
}
fluxprobe0
{
type surfaceFieldValue;
libs ("libfieldFunctionObjects.so");
writeControl timeStep;
writeInterval 100;
log true;
writeFields false;
regionType faceZone;
name fzcenter;
operation sum;
fields
(
phi
);
}
fluxprobe1
{
type surfaceFieldValue;
libs ("libfieldFunctionObjects.so");
writeControl timeStep;
writeInterval 100;
log true;
writeFields false;
regionType faceZone;
name fz0;
operation sum;
fields
(
phi
);
}
fieldAverage1 fieldAverage1
{ {
type fieldAverage; type fieldAverage;
@ -125,13 +182,12 @@ functions
); );
} }
fieldOutput fieldOutput
{ {
type writeObjects; type writeObjects;
functionObjectLibs ( "libutilityFunctionObjects.so" ); functionObjectLibs ( "libutilityFunctionObjects.so" );
exclusiveWriting true; exclusiveWriting true;
objects ("rhoRecMean" "voidfraction" "voidfractionRec" "voidfractionMean" "voidfractionRecMean" "addSourceMean" "phiSMean" "TMean" "T" "particleTemp" "particleTempMean"); objects ("rhoRecMean" "voidfraction" "voidfractionRec" "voidfractionMean" "voidfractionRecMean" "addSourceMean" "TMean" "T" "partTemp" "partTempMean");
writeControl timeStep; writeControl timeStep;
writeInterval 40000; writeInterval 40000;
} }
@ -177,10 +233,10 @@ functions
scalarList newWeights(2); scalarList newWeights(2);
newWeights[0] = w0; newWeights[0] = w0;
newWeights[1] = 1-w0; newWeights[1] = 1-w0;
/*
scalarList newWeights(1); // scalarList newWeights(1);
newWeights[0] = 1.0; // newWeights[0] = 1.0;
*/
weightDict.set("weights",newWeights); weightDict.set("weights",newWeights);
#}; #};
} }

View File

@ -28,13 +28,6 @@ gradSchemes
divSchemes divSchemes
{ {
default Gauss linear; default Gauss linear;
div(phi,U) Gauss limitedLinearV 1;
div(phi,k) Gauss limitedLinear 1;
div(phi,epsilon) Gauss limitedLinear 1;
div(phi,R) Gauss limitedLinear 1;
div(R) Gauss linear;
div(phi,nuTilda) Gauss limitedLinear 1;
div((nuEff*dev(T(grad(U))))) Gauss linear;
div(phi,T) Gauss limitedLinear 1; div(phi,T) Gauss limitedLinear 1;
// div(phi,T) Gauss upwind; // div(phi,T) Gauss upwind;
} }
@ -57,7 +50,6 @@ snGradSchemes
fluxRequired fluxRequired
{ {
default no; default no;
p ;
T ; T ;
} }

View File

@ -17,14 +17,6 @@ FoamFile
solvers solvers
{ {
"(p|rho)"
{
solver PCG;
preconditioner DIC;
tolerance 1e-6;
relTol 0.01;
}
"(correctedField)" "(correctedField)"
{ {
solver PCG; solver PCG;
@ -33,26 +25,6 @@ solvers
relTol 0.05; relTol 0.05;
} }
"(p|rho)Final"
{
$p;
relTol 0;
}
"(U|k|e|epsilon|R|nuTilda|c)"
{
solver smoothSolver;
smoother GaussSeidel;
tolerance 1e-05;
relTol 0;
}
"(U|e|k|nuTilda)Final"
{
$U;
relTol 0;
}
T T
{ {
solver PBiCG; solver PBiCG;

View File

@ -39,7 +39,6 @@ variable rfPW2 equal 0.1
variable Tpart equal 330 variable Tpart equal 330
variable dt equal 0.0025 variable dt equal 0.0025
#0.001
variable skin equal 0.0005 variable skin equal 0.0005
############################################### ###############################################
@ -112,13 +111,9 @@ variable Tave equal v_sumT1/v_np
fix printheat all print 10 "${time} ${Tave}" file ../DEM/temp_ave.txt title "#time T_ave" fix printheat all print 10 "${time} ${Tave}" file ../DEM/temp_ave.txt title "#time T_ave"
#fix tdist1 all ave/histo 1000 1 1000 324 380 56 f_Temp[0] mode vector file ../DEM/temp_histo.txt title1 "Particle temperatures [K]"
#fix tdist2 all ave/histo 1000 1 1000 324 380 448 f_Temp[0] mode vector file ../DEM/temp_histo_fine.txt title1 "Particle temperatures [K]"
fix tdist1 all ave/histo 400 1 400 324 380 56 f_Temp[0] mode vector file ../DEM/temp_histo.txt title1 "Particle temperatures [K]" fix tdist1 all ave/histo 400 1 400 324 380 56 f_Temp[0] mode vector file ../DEM/temp_histo.txt title1 "Particle temperatures [K]"
fix tdist2 all ave/histo 400 1 400 324 380 448 f_Temp[0] mode vector file ../DEM/temp_histo_fine.txt title1 "Particle temperatures [K]" fix tdist2 all ave/histo 400 1 400 324 380 448 f_Temp[0] mode vector file ../DEM/temp_histo_fine.txt title1 "Particle temperatures [K]"
fix integr all nve/sphere fix integr all nve/sphere
#screen output #screen output
@ -131,3 +126,6 @@ dump dmp all custom/vtk 10000 ../DEM/post/dump*.liggghts_coupled.vtk id type x
run 1 run 1
set region total property/atom Temp ${Tpart} set region total property/atom Temp ${Tpart}
# heat sources are already set in the restart file; if they would not have been - or if restarting in a different way -, set them now
#set region insReg property/atom heatSource 3.3379e-04 # = V_p x \dot{q}