CFD Online Logo CFD Online URL
www.cfd-online.com
[Sponsors]
Home > Forums > Software User Forums > OpenFOAM > OpenFOAM Post-Processing

How to calculate the LES turbulent kinetic erengy in OpenFOAM

Register Blogs Community New Posts Updated Threads Search

Like Tree16Likes
  • 1 Post By wangziyang
  • 4 Post By cjc96
  • 9 Post By Luiz
  • 1 Post By Luiz
  • 1 Post By NLeb

Reply
 
LinkBack Thread Tools Search this Thread Display Modes
Old   February 25, 2020, 01:56
Post How to calculate the LES turbulent kinetic erengy in OpenFOAM
  #1
New Member
 
王子阳
Join Date: Aug 2019
Posts: 29
Rep Power: 6
wangziyang is on a distinguished road
hi

i recently want to calculate the turbulent kinetic erengy using LES,

when i search on the net, i only search the formula: k= 0.5((u')^2+(v')^2+(w')^2)

where,u'=u-umean,v'=v-vmean,w'=w-wmean


i think this formula is uncorrect,but i can't find how to calculate LES TKE in openfoam

help!

best wishes!

ziwang
Светлана likes this.
wangziyang is offline   Reply With Quote

Old   February 27, 2020, 07:57
Default
  #2
Member
 
Conor Crickmore
Join Date: Jan 2020
Location: Leicestershire, United Kingdom
Posts: 36
Rep Power: 6
cjc96 is on a distinguished road
Hey!

This is asked quite a lot on the forum, you'll probably find a fair few discussions about if you were to type in "LES TKE CFD-Online" into Google. Your formula for Turbulent Turbulent Kinetic Energy is (more or less) correct.

I've recently posted a thread where I was working on a function to output the ratio of resolved/total TKE for my own LES work, see here.

The quick version of which is that the 'R' post-processing function will provide you with the sub-grid Reynolds Stress Tensor, and the 'UPrime2Mean' calculation in the 'fieldAverage' function will provide you with the resolved Reynolds Stress Tensor, where:

k = \frac{1}{2}tr(R)

so your total Turbulent Kinetic Energy is:

k_{total} = k_{sub-grid} + k_{resolved} = \frac{1}{2}tr(R) + \frac{1}{2}tr(UPrime2Mean)

Hopefully this and the links provided should be enough to see you through!
__________________
Conor Crickmore
PhD Researcher in Automotive Aerodynamics
Aeronautical and Automotive Engineering
Loughborough University
LE11 3TU
cjc96 is offline   Reply With Quote

Old   August 27, 2020, 16:51
Default
  #3
New Member
 
Luiz Oliveira
Join Date: Aug 2018
Location: Napoli, Italy
Posts: 24
Rep Power: 7
Luiz is on a distinguished road
Since someone might be as lazy as myself, here goes the code that adds the totalTKE into account:
Code:
totalTKE
{
    type            coded;
    libs            ("libutilityFunctionObjects.so");
    name            totalTKE;
    executeControl    timeStep;
    writeControl    writeTime;
    // timeStart        0;
    // timeEnd        0;
    enabled            true;

/*---------------------------------------------------------------------------*\

    Total Turbulent Kinect Energy Evaluation
        ** Requires fieldAverage Function to Obtain UPrime2Mean**
            ** Resolved Reynolds Stress Tensor
        ** Requires turbulenceFields Function to Obtain R**
            ** Subgrid Reynolds Stress Tensor

\*---------------------------------------------------------------------------*/

    codeExecute
    #{
        static autoPtr<volScalarField> totalTKE;

        if
        (
            mesh().foundObject<volSymmTensorField>("UPrime2Mean")
            &&
            mesh().foundObject<volSymmTensorField>("turbulenceProperties:R")
            &&
            mesh().foundObject<volScalarField>("totalTKE") == 0
        )
        {
            Info << "Turbulent Kinect Energy:" << endl;
            Info << "    Initialising" << endl;
            Info << "    Calculating" << nl << endl;

            totalTKE.set
            (
                new volScalarField
                (
                    IOobject
                    (
                        "totalTKE",
                        mesh().time().timeName(),
                        mesh(),
                        IOobject::NO_READ,
                        IOobject::AUTO_WRITE
                    ),
                    mesh(),
                    dimensionedScalar
                    (
                        "totalTKE",
                        dimensionSet(0,2,-2,0,0,0,0),
                        0
                    )
                )
            );

            const volSymmTensorField& R = mesh().lookupObjectRef<volSymmTensorField>("turbulenceProperties:R");
            const volSymmTensorField& UPrime2Mean = mesh().lookupObjectRef<volSymmTensorField>("UPrime2Mean");

            volScalarField& totalTKE = mesh().lookupObjectRef<volScalarField>("totalTKE");
            totalTKE = (0.5 * tr(R)) + (0.5 * tr(UPrime2Mean));
            totalTKE.write();
        }

        else if
        (
            mesh().foundObject<volSymmTensorField>("UPrime2Mean")
            &&
            mesh().foundObject<volSymmTensorField>("turbulenceProperties:R")
            &&
            mesh().foundObject<volScalarField>("totalTKE")
        )
        {
            Info << "Turbulent Kinect Energy:" << endl;
            Info << "    Calculating" << nl << endl;

            const volSymmTensorField& R = mesh().lookupObjectRef<volSymmTensorField>("turbulenceProperties:R");
            const volSymmTensorField& UPrime2Mean = mesh().lookupObjectRef<volSymmTensorField>("UPrime2Mean");

            volScalarField& totalTKE = mesh().lookupObjectRef<volScalarField>("totalTKE");
            totalTKE = (0.5 * tr(R)) + (0.5 * tr(UPrime2Mean));
            totalTKE.write();
        }

        else
        {
            Info << "Turbulent Kinect Energy:" << endl;
            Warning << endl
                    << "    Unable to Calculate Turbulent Kinect Energy" << endl
                    << "    UPrime2Mean and/or R Unavailable" << endl
                    << "    Enable fieldAverage and turbulenceFields Functions" << nl << endl;
        }
    #};
}
Note that this most be in system folder and called by controlDict.
The only changes from cjc96 function are the referencing to R (from R to turbulenceProperties:R) and the calculation itself. I checked function results with some literature data available and it seems to yield adequate values.
oswald, Farid, zhangyan and 6 others like this.
__________________
Luiz Oliveira
PhD. Student in Environmental Fluid Dynamics
University of Napoli: Federico II
Luiz is offline   Reply With Quote

Old   December 25, 2020, 11:08
Default
  #4
New Member
 
Anonymous
Join Date: Oct 2019
Location: Canada
Posts: 1
Rep Power: 0
yarrald is on a distinguished road
Does the order of the functions call matter? If I want to time average the totalTKE so I can compare it to RANS, I need to do the following:

fieldAverage U to get Uprime2Mean
turbulenceProperties to get R
totalTKE function to using the above two
fieldAverage TKE to get the time average of the above.

Obviously there are various calls in here, will openFOAM handle this so long as they are all in the controlDict? Or do I need to place them in the order they need to be called?
yarrald is offline   Reply With Quote

Old   December 26, 2020, 10:45
Default
  #5
New Member
 
Luiz Oliveira
Join Date: Aug 2018
Location: Napoli, Italy
Posts: 24
Rep Power: 7
Luiz is on a distinguished road
Yes, the order of the function matters when calling it. Personally, I add the totalTKE as an external file, so in the controlDict I only include this function, similar to what you do with residuals. But nothing stops you from adding it all to the controlDict file, it should work exactly the same.

The order you presented is fine and this should work. A noticed bug occurs when you start totalTKE along with the field average and the R function it will not identify the required fields and most likely crash. A quick fix for this is making it start one timestep after the fieldAveraging and the R start.

Also, it will save at each timestep. you can disable this by deleting the line
Code:
totalTKE.write();
By doing so you can use the normal time controls available in openFOAM (eg. timeStart, timeEnd, writeTime ...)
ERKSMAFA likes this.
__________________
Luiz Oliveira
PhD. Student in Environmental Fluid Dynamics
University of Napoli: Federico II
Luiz is offline   Reply With Quote

Old   April 11, 2022, 06:32
Default How to add this to the controlDict
  #6
New Member
 
Ali
Join Date: Dec 2016
Location: Hong Kong
Posts: 12
Rep Power: 9
abas.rahmani86 is on a distinguished road
Quote:
Originally Posted by Luiz View Post
Since someone might be as lazy as myself, here goes the code that adds the totalTKE into account:
Code:
totalTKE
{
    type            coded;
    libs            ("libutilityFunctionObjects.so");
    name            totalTKE;
    executeControl    timeStep;
    writeControl    writeTime;
    // timeStart        0;
    // timeEnd        0;
    enabled            true;

/*---------------------------------------------------------------------------*\

    Total Turbulent Kinect Energy Evaluation
        ** Requires fieldAverage Function to Obtain UPrime2Mean**
            ** Resolved Reynolds Stress Tensor
        ** Requires turbulenceFields Function to Obtain R**
            ** Subgrid Reynolds Stress Tensor

\*---------------------------------------------------------------------------*/

    codeExecute
    #{
        static autoPtr<volScalarField> totalTKE;

        if
        (
            mesh().foundObject<volSymmTensorField>("UPrime2Mean")
            &&
            mesh().foundObject<volSymmTensorField>("turbulenceProperties:R")
            &&
            mesh().foundObject<volScalarField>("totalTKE") == 0
        )
        {
            Info << "Turbulent Kinect Energy:" << endl;
            Info << "    Initialising" << endl;
            Info << "    Calculating" << nl << endl;

            totalTKE.set
            (
                new volScalarField
                (
                    IOobject
                    (
                        "totalTKE",
                        mesh().time().timeName(),
                        mesh(),
                        IOobject::NO_READ,
                        IOobject::AUTO_WRITE
                    ),
                    mesh(),
                    dimensionedScalar
                    (
                        "totalTKE",
                        dimensionSet(0,2,-2,0,0,0,0),
                        0
                    )
                )
            );

            const volSymmTensorField& R = mesh().lookupObjectRef<volSymmTensorField>("turbulenceProperties:R");
            const volSymmTensorField& UPrime2Mean = mesh().lookupObjectRef<volSymmTensorField>("UPrime2Mean");

            volScalarField& totalTKE = mesh().lookupObjectRef<volScalarField>("totalTKE");
            totalTKE = (0.5 * tr(R)) + (0.5 * tr(UPrime2Mean));
            totalTKE.write();
        }

        else if
        (
            mesh().foundObject<volSymmTensorField>("UPrime2Mean")
            &&
            mesh().foundObject<volSymmTensorField>("turbulenceProperties:R")
            &&
            mesh().foundObject<volScalarField>("totalTKE")
        )
        {
            Info << "Turbulent Kinect Energy:" << endl;
            Info << "    Calculating" << nl << endl;

            const volSymmTensorField& R = mesh().lookupObjectRef<volSymmTensorField>("turbulenceProperties:R");
            const volSymmTensorField& UPrime2Mean = mesh().lookupObjectRef<volSymmTensorField>("UPrime2Mean");

            volScalarField& totalTKE = mesh().lookupObjectRef<volScalarField>("totalTKE");
            totalTKE = (0.5 * tr(R)) + (0.5 * tr(UPrime2Mean));
            totalTKE.write();
        }

        else
        {
            Info << "Turbulent Kinect Energy:" << endl;
            Warning << endl
                    << "    Unable to Calculate Turbulent Kinect Energy" << endl
                    << "    UPrime2Mean and/or R Unavailable" << endl
                    << "    Enable fieldAverage and turbulenceFields Functions" << nl << endl;
        }
    #};
}
Note that this most be in system folder and called by controlDict.
The only changes from cjc96 function are the referencing to R (from R to turbulenceProperties:R) and the calculation itself. I checked function results with some literature data available and it seems to yield adequate values.
Thank you for sharing the script. Please help me to find how to add this to the controlDict. If it is possible, please share a system file that uses it.
abas.rahmani86 is offline   Reply With Quote

Old   July 14, 2022, 04:10
Default
  #7
New Member
 
Nik
Join Date: Apr 2021
Posts: 7
Rep Power: 5
NLeb is on a distinguished road
Here's all you need to add at the bottom of your controlDict to get it working. If there is an existing "functions" section in your controlDict, then just combine their contents together. This was on OpenFOAMv2206.

Code:
functions
{
    fieldAverage
    {
        type            fieldAverage;
        libs            (fieldFunctionObjects);
        executeControl  timeStep;
        writeControl    writeTime;
        enabled         true;
        
        fields
        (
            U
            {
                mean            yes;
                prime2Mean      yes;
                base            time;
            }
        );
    }

    turbulenceFields
    {
        type            turbulenceFields;
        libs            (fieldFunctionObjects);
        executeControl  timeStep;
        writeControl    writeTime;
        enabled         true;

        field           R;
    }

    totalTKE
    {
        type            coded;
        libs            ("libutilityFunctionObjects.so");
        name            totalTKE;
        executeControl  timeStep;
        writeControl    writeTime;
        enabled         true;

    /*---------------------------------------------------------------------------*\

        Total Turbulent Kinect Energy Evaluation
            ** Requires fieldAverage Function to Obtain UPrime2Mean**
                ** Resolved Reynolds Stress Tensor
            ** Requires turbulenceFields Function to Obtain R**
                ** Subgrid Reynolds Stress Tensor

    \*---------------------------------------------------------------------------*/

        codeExecute
        #{
            static autoPtr<volScalarField> totalTKE;

            if
            (
                mesh().foundObject<volSymmTensorField>("UPrime2Mean")
                &&
                mesh().foundObject<volSymmTensorField>("turbulenceProperties:R")
                &&
                mesh().foundObject<volScalarField>("totalTKE") == 0
            )
            {
                Info << "Turbulent Kinect Energy:" << endl;
                Info << "    Initialising" << endl;
                Info << "    Calculating" << nl << endl;

                totalTKE.set
                (
                    new volScalarField
                    (
                        IOobject
                        (
                            "totalTKE",
                            mesh().time().timeName(),
                            mesh(),
                            IOobject::NO_READ,
                            IOobject::AUTO_WRITE
                        ),
                        mesh(),
                        dimensionedScalar
                        (
                            "totalTKE",
                            dimensionSet(0,2,-2,0,0,0,0),
                            0
                        )
                    )
                );

                const volSymmTensorField& R = mesh().lookupObjectRef<volSymmTensorField>("turbulenceProperties:R");
                const volSymmTensorField& UPrime2Mean = mesh().lookupObjectRef<volSymmTensorField>("UPrime2Mean");

                volScalarField& totalTKE = mesh().lookupObjectRef<volScalarField>("totalTKE");
                totalTKE = (0.5 * tr(R)) + (0.5 * tr(UPrime2Mean));
                totalTKE.write();
            }

            else if
            (
                mesh().foundObject<volSymmTensorField>("UPrime2Mean")
                &&
                mesh().foundObject<volSymmTensorField>("turbulenceProperties:R")
                &&
                mesh().foundObject<volScalarField>("totalTKE")
            )
            {
                Info << "Turbulent Kinect Energy:" << endl;
                Info << "    Calculating" << nl << endl;

                const volSymmTensorField& R = mesh().lookupObjectRef<volSymmTensorField>("turbulenceProperties:R");
                const volSymmTensorField& UPrime2Mean = mesh().lookupObjectRef<volSymmTensorField>("UPrime2Mean");

                volScalarField& totalTKE = mesh().lookupObjectRef<volScalarField>("totalTKE");
                totalTKE = (0.5 * tr(R)) + (0.5 * tr(UPrime2Mean));
                totalTKE.write();
            }

            else
            {
                Info << "Turbulent Kinect Energy:" << endl;
                Warning << endl
                        << "    Unable to Calculate Turbulent Kinect Energy" << endl
                        << "    UPrime2Mean and/or R Unavailable" << endl
                        << "    Enable fieldAverage and turbulenceFields Functions" << nl << endl;
            }
        #};
    }
}
nukecrafts likes this.
NLeb is offline   Reply With Quote

Old   July 16, 2023, 13:33
Default
  #8
Member
 
Join Date: Jan 2017
Posts: 71
Rep Power: 9
sadsid is on a distinguished road
Can we also use this approach in the case of the Smagorinsky model?

Quote:
Originally Posted by NLeb View Post
Here's all you need to add at the bottom of your controlDict to get it working. If there is an existing "functions" section in your controlDict, then just combine their contents together. This was on OpenFOAMv2206.

Code:
functions
{
    fieldAverage
    {
        type            fieldAverage;
        libs            (fieldFunctionObjects);
        executeControl  timeStep;
        writeControl    writeTime;
        enabled         true;
        
        fields
        (
            U
            {
                mean            yes;
                prime2Mean      yes;
                base            time;
            }
        );
    }

    turbulenceFields
    {
        type            turbulenceFields;
        libs            (fieldFunctionObjects);
        executeControl  timeStep;
        writeControl    writeTime;
        enabled         true;

        field           R;
    }

    totalTKE
    {
        type            coded;
        libs            ("libutilityFunctionObjects.so");
        name            totalTKE;
        executeControl  timeStep;
        writeControl    writeTime;
        enabled         true;

    /*---------------------------------------------------------------------------*\

        Total Turbulent Kinect Energy Evaluation
            ** Requires fieldAverage Function to Obtain UPrime2Mean**
                ** Resolved Reynolds Stress Tensor
            ** Requires turbulenceFields Function to Obtain R**
                ** Subgrid Reynolds Stress Tensor

    \*---------------------------------------------------------------------------*/

        codeExecute
        #{
            static autoPtr<volScalarField> totalTKE;

            if
            (
                mesh().foundObject<volSymmTensorField>("UPrime2Mean")
                &&
                mesh().foundObject<volSymmTensorField>("turbulenceProperties:R")
                &&
                mesh().foundObject<volScalarField>("totalTKE") == 0
            )
            {
                Info << "Turbulent Kinect Energy:" << endl;
                Info << "    Initialising" << endl;
                Info << "    Calculating" << nl << endl;

                totalTKE.set
                (
                    new volScalarField
                    (
                        IOobject
                        (
                            "totalTKE",
                            mesh().time().timeName(),
                            mesh(),
                            IOobject::NO_READ,
                            IOobject::AUTO_WRITE
                        ),
                        mesh(),
                        dimensionedScalar
                        (
                            "totalTKE",
                            dimensionSet(0,2,-2,0,0,0,0),
                            0
                        )
                    )
                );

                const volSymmTensorField& R = mesh().lookupObjectRef<volSymmTensorField>("turbulenceProperties:R");
                const volSymmTensorField& UPrime2Mean = mesh().lookupObjectRef<volSymmTensorField>("UPrime2Mean");

                volScalarField& totalTKE = mesh().lookupObjectRef<volScalarField>("totalTKE");
                totalTKE = (0.5 * tr(R)) + (0.5 * tr(UPrime2Mean));
                totalTKE.write();
            }

            else if
            (
                mesh().foundObject<volSymmTensorField>("UPrime2Mean")
                &&
                mesh().foundObject<volSymmTensorField>("turbulenceProperties:R")
                &&
                mesh().foundObject<volScalarField>("totalTKE")
            )
            {
                Info << "Turbulent Kinect Energy:" << endl;
                Info << "    Calculating" << nl << endl;

                const volSymmTensorField& R = mesh().lookupObjectRef<volSymmTensorField>("turbulenceProperties:R");
                const volSymmTensorField& UPrime2Mean = mesh().lookupObjectRef<volSymmTensorField>("UPrime2Mean");

                volScalarField& totalTKE = mesh().lookupObjectRef<volScalarField>("totalTKE");
                totalTKE = (0.5 * tr(R)) + (0.5 * tr(UPrime2Mean));
                totalTKE.write();
            }

            else
            {
                Info << "Turbulent Kinect Energy:" << endl;
                Warning << endl
                        << "    Unable to Calculate Turbulent Kinect Energy" << endl
                        << "    UPrime2Mean and/or R Unavailable" << endl
                        << "    Enable fieldAverage and turbulenceFields Functions" << nl << endl;
            }
        #};
    }
}
sadsid is offline   Reply With Quote

Reply

Tags
tke les


Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are Off
Pingbacks are On
Refbacks are On


Similar Threads
Thread Thread Starter Forum Replies Last Post
OpenFOAM v3.0+ ?? SBusch OpenFOAM 22 December 26, 2016 14:24
How to calculate turbulent kinetic energy at first grid point in SST k-o dinhanh Main CFD Forum 1 December 19, 2016 09:54
OpenFOAM LES capability questions siw OpenFOAM Running, Solving & CFD 3 January 6, 2015 08:50
Subgrid Turbulent Kinetic Energy in LES saqure ANSYS 3 September 7, 2012 16:44
New OpenFOAM Forum Structure jola OpenFOAM 2 October 19, 2011 06:55


All times are GMT -4. The time now is 19:42.