Difference between revisions of "ScalarTransportFoam"
Line 33: | Line 33: | ||
where <math>T</math> is the transported scalar, <math>\mathbf{U}</math> is the fluid velocity, and <math>\mathcal{D}_{\textrm{T}}</math> is the diffusion coefficient divided by the fluid density, both supposed to be constant. | where <math>T</math> is the transported scalar, <math>\mathbf{U}</math> is the fluid velocity, and <math>\mathcal{D}_{\textrm{T}}</math> is the diffusion coefficient divided by the fluid density, both supposed to be constant. | ||
+ | |||
+ | == scalarTransportFoam implementation == | ||
+ | |||
+ | === Numerical methodology and solution procedure === | ||
+ | |||
+ | The numerical methodology used to solve the scalar trasnport equation in scalarTransportFoam is based on the finite volume technique. In particular, all the terms of the equations are discretized implicitly, using the fvm family of operators. | ||
+ | |||
+ | === Code representation === | ||
+ | The implementation of a scalar transport equation in OpenFOAM(r) is straightforward due to its advanced C++ syntax. A few preliminary steps are necessary however to define the fields involved in the terms of the transport equation. | ||
+ | |||
+ | ==== Field definition ==== | ||
+ | In order to solve the scalar transport equation, the scalar field for <math>T</math> and the vector field for | ||
+ | <math>\mathbf{U}</math> must be defined, as well as the diffusion coefficient has to be declared and its value must be known. This is managed in the code in the createFields.H header file. | ||
+ | |||
+ | Since this is a basic solver, it is worth to spend a few words on the implementation details, which will be useful to interpret the code of more complex solvers in other guides. In the main body of the solver reported below | ||
+ | |||
+ | <cpp> | ||
+ | #include "fvCFD.H" | ||
+ | |||
+ | int main(int argc, char *argv[]) | ||
+ | { | ||
+ | |||
+ | # include "setRootCase.H" | ||
+ | |||
+ | # include "createTime.H" | ||
+ | # include "createMesh.H" | ||
+ | # include "createFields.H" | ||
+ | |||
+ | |||
+ | Info<< "\nCalculating scalar transport\n" << endl; | ||
+ | |||
+ | # include "CourantNo.H" | ||
+ | |||
+ | while (runTime.loop()) | ||
+ | { | ||
+ | Info<< "Time = " << runTime.timeName() << nl << endl; | ||
+ | |||
+ | # include "readSIMPLEControls.H" | ||
+ | |||
+ | for (int nonOrth=0; nonOrth<=nNonOrthCorr; nonOrth++) | ||
+ | { | ||
+ | solve | ||
+ | ( | ||
+ | fvm::ddt(T) | ||
+ | + fvm::div(phi, T) | ||
+ | - fvm::laplacian(DT, T) | ||
+ | ); | ||
+ | } | ||
+ | |||
+ | runTime.write(); | ||
+ | } | ||
+ | |||
+ | Info<< "End\n" << endl; | ||
+ | |||
+ | return 0; | ||
+ | } | ||
+ | </cpp> | ||
+ | |||
+ | we notice that one main header, fvCFD.H, is included at the top of the code. This header contains a series of other include directives, whose purpose is to make basic OpenFOAM functionalities available in the code. In the following line, | ||
+ | |||
+ | <cpp> | ||
+ | Info<< "Reading field T\n" << endl; | ||
+ | |||
+ | volScalarField T | ||
+ | ( | ||
+ | IOobject | ||
+ | ( | ||
+ | "T", | ||
+ | runTime.timeName(), | ||
+ | mesh, | ||
+ | IOobject::MUST_READ, | ||
+ | IOobject::AUTO_WRITE | ||
+ | ), | ||
+ | mesh | ||
+ | ); | ||
+ | |||
+ | |||
+ | Info<< "Reading field U\n" << endl; | ||
+ | |||
+ | volVectorField U | ||
+ | ( | ||
+ | IOobject | ||
+ | ( | ||
+ | "U", | ||
+ | runTime.timeName(), | ||
+ | mesh, | ||
+ | IOobject::MUST_READ, | ||
+ | IOobject::AUTO_WRITE | ||
+ | ), | ||
+ | mesh | ||
+ | ); | ||
+ | </cpp> | ||
+ | |||
+ | <cpp> | ||
+ | Info<< "Reading transportProperties\n" << endl; | ||
+ | |||
+ | IOdictionary transportProperties | ||
+ | ( | ||
+ | IOobject | ||
+ | ( | ||
+ | "transportProperties", | ||
+ | runTime.constant(), | ||
+ | mesh, | ||
+ | IOobject::MUST_READ, | ||
+ | IOobject::NO_WRITE | ||
+ | ) | ||
+ | ); | ||
+ | |||
+ | </cpp> | ||
+ | |||
+ | |||
+ | <cpp> | ||
+ | Info<< "Reading diffusivity D\n" << endl; | ||
+ | |||
+ | dimensionedScalar DT | ||
+ | ( | ||
+ | transportProperties.lookup("DT") | ||
+ | ); | ||
+ | |||
+ | # include "createPhi.H" | ||
+ | </cpp> | ||
[[Category:Basic CFD solvers]] | [[Category:Basic CFD solvers]] |
Revision as of 05:11, 17 February 2010
Contents
1 Introduction and applications
The scalarTransportFoam is a basic solver which resolves a transport equation for a passive scalar, using a user-specified stationary velocity field.
Typical applications are:
- Solution of a scalar convection-diffusion problem on a given velocity field.
2 scalarTransportFoam features, capabilities and limitations
3 scalarTransportFoam capabilities
The scalarTransportFoam solver implements and solves a convection-diffusion scalar transport equation without source terms.
The main features of the solver are:
- Solution of a convection-diffusion equation with user-specified boundary conditions
- Arbitrary velocity field provided by the user and read at runtime
4 scalarTransportFoam limitations
The main limitations of the solver are:
- The diffusion coefficient is assumed to be a constant scalar
- An option to solve for the flow coupled with the scalar transport is not available
5 scalarTransportFoam theory
The scalarTransportFoam solver uses a complete convection-diffusion equation, in the incompressible form (the equation is divided by the density)
where is the transported scalar, is the fluid velocity, and is the diffusion coefficient divided by the fluid density, both supposed to be constant.
6 scalarTransportFoam implementation
6.1 Numerical methodology and solution procedure
The numerical methodology used to solve the scalar trasnport equation in scalarTransportFoam is based on the finite volume technique. In particular, all the terms of the equations are discretized implicitly, using the fvm family of operators.
6.2 Code representation
The implementation of a scalar transport equation in OpenFOAM(r) is straightforward due to its advanced C++ syntax. A few preliminary steps are necessary however to define the fields involved in the terms of the transport equation.
6.2.1 Field definition
In order to solve the scalar transport equation, the scalar field for and the vector field for must be defined, as well as the diffusion coefficient has to be declared and its value must be known. This is managed in the code in the createFields.H header file.
Since this is a basic solver, it is worth to spend a few words on the implementation details, which will be useful to interpret the code of more complex solvers in other guides. In the main body of the solver reported below
#include "fvCFD.H" int main(int argc, char *argv[]) { # include "setRootCase.H" # include "createTime.H" # include "createMesh.H" # include "createFields.H" Info<< "\nCalculating scalar transport\n" << endl; # include "CourantNo.H" while (runTime.loop()) { Info<< "Time = " << runTime.timeName() << nl << endl; # include "readSIMPLEControls.H" for (int nonOrth=0; nonOrth<=nNonOrthCorr; nonOrth++) { solve ( fvm::ddt(T) + fvm::div(phi, T) - fvm::laplacian(DT, T) ); } runTime.write(); } Info<< "End\n" << endl; return 0; }
we notice that one main header, fvCFD.H, is included at the top of the code. This header contains a series of other include directives, whose purpose is to make basic OpenFOAM functionalities available in the code. In the following line,
Info<< "Reading field T\n" << endl; volScalarField T ( IOobject ( "T", runTime.timeName(), mesh, IOobject::MUST_READ, IOobject::AUTO_WRITE ), mesh ); Info<< "Reading field U\n" << endl; volVectorField U ( IOobject ( "U", runTime.timeName(), mesh, IOobject::MUST_READ, IOobject::AUTO_WRITE ), mesh );
Info<< "Reading transportProperties\n" << endl; IOdictionary transportProperties ( IOobject ( "transportProperties", runTime.constant(), mesh, IOobject::MUST_READ, IOobject::NO_WRITE ) );
Info<< "Reading diffusivity D\n" << endl; dimensionedScalar DT ( transportProperties.lookup("DT") ); # include "createPhi.H"