View Issue Details
ID | Project | Category | View Status | Date Submitted | Last Update |
---|---|---|---|---|---|
0000953 | OpenFOAM | Bug | public | 2013-08-12 16:59 | 2016-02-03 13:21 |
Reporter | dkxls | Assigned To | henry | ||
Priority | high | Severity | minor | Reproducibility | always |
Status | closed | Resolution | no change required | ||
Platform | Linux x86_64 | OS | openSUSE | OS Version | 12.2 |
Summary | 0000953: [Lagrangian]: Missing Lagrangian sub-cycle (i.e. the Lagrangian time-step) setting | ||||
Description | In the current implementation the Lagrangian sub-cycles (i.e. the Lagrangian time-step) cannot be set by the user. The number of sub-cycles is always 1 (i.e. carrierDt = lagrangianDt), except during injection. I believe, this feature requires only minor changes, as all necessary infrastructure is implemented already! The changes would only concern the following step: 1. reading the number of sub-cycles from the dictionary (probably best in cloudSolution) 2. set 'dtMax = tEnd/nSubCycle' (in the function Foam::KinematicParcel<ParcelType>::move) Lagrangian sub-cycles are important/necessary to achieve a stable solution in many spray simulation and this has been a feature of the dieselSpray implementation. | ||||
Additional Information | lagrangian/intermediate/parcels/Templates/KinematicParcel/KinematicParcel.C https://github.com/OpenFOAM/OpenFOAM-2.0.x/blob/master/src/lagrangian/dieselSpray/parcel/parcel.C | ||||
Tags | contribution, Lagrangian, spray, sprayEngineFoam, sprayFoam | ||||
|
0001-Add-subcycles-to-Lagrangian.patch (4,581 bytes)
From 1814a83f01ac833f0a28e537579e6674f8cd3df3 Mon Sep 17 00:00:00 2001 From: Armin Wehrfritz <armin.wehrfritz@aalto.fi> Date: Tue, 13 Aug 2013 21:28:36 +0300 Subject: [PATCH] Add subcycles to Lagrangian --- .../Templates/KinematicCloud/cloudSolution/cloudSolution.C | 9 +++++++++ .../Templates/KinematicCloud/cloudSolution/cloudSolution.H | 7 +++++++ .../Templates/KinematicCloud/cloudSolution/cloudSolutionI.H | 6 ++++++ .../parcels/Templates/KinematicParcel/KinematicParcel.C | 2 +- 4 files changed, 23 insertions(+), 1 deletion(-) diff --git a/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolution.C b/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolution.C index fd7bf31..70da8f4 100644 --- a/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolution.C +++ b/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolution.C @@ -38,6 +38,7 @@ Foam::cloudSolution::cloudSolution dict_(dict), active_(dict.lookup("active")), transient_(false), + subCycles_(1), calcFrequency_(1), maxCo_(0.3), iter_(1), @@ -64,6 +65,7 @@ Foam::cloudSolution::cloudSolution dict_(cs.dict_), active_(cs.active_), transient_(cs.transient_), + subCycles_(cs.subCycles_), calcFrequency_(cs.calcFrequency_), maxCo_(cs.maxCo_), iter_(cs.iter_), @@ -85,6 +87,7 @@ Foam::cloudSolution::cloudSolution dict_(dictionary::null), active_(false), transient_(false), + subCycles_(1), calcFrequency_(0), maxCo_(GREAT), iter_(0), @@ -123,6 +126,12 @@ void Foam::cloudSolution::read() >> resetSourcesOnStartup_; } } + else + { + dict_.lookup("subCycles") >> subCycles_; + subCycles_ = max(subCycles_,1); +// dict_.lookupOrDefault<int>("subCycles",1) >> subCycles_; + } if (coupled_) { diff --git a/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolution.H b/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolution.H index e155abc..eac387b 100644 --- a/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolution.H +++ b/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolution.H @@ -65,6 +65,10 @@ class cloudSolution //- Transient flag Switch transient_; + //- Sub cycles - cloud steps per carrier step + // NOTE: Transient operation only + label subCycles_; + //- Calculation frequency - carrier steps per cloud step // NOTE: Steady operation only label calcFrequency_; @@ -156,6 +160,9 @@ public: //- Return const access to the steady flag inline const Switch steadyState() const; + //- Return const access to the sub cycles + inline const label subCycles() const; + //- Return const access to the calculation frequency inline label calcFrequency() const; diff --git a/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolutionI.H b/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolutionI.H index 6280b97..64672e2 100644 --- a/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolutionI.H +++ b/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolutionI.H @@ -71,6 +71,12 @@ inline const Foam::Switch Foam::cloudSolution::steadyState() const } +inline const Foam::label Foam::cloudSolution::subCycles() const +{ + return subCycles_; +} + + inline Foam::label Foam::cloudSolution::calcFrequency() const { return calcFrequency_; diff --git a/src/lagrangian/intermediate/parcels/Templates/KinematicParcel/KinematicParcel.C b/src/lagrangian/intermediate/parcels/Templates/KinematicParcel/KinematicParcel.C index 7ec52b1..cbd3417 100644 --- a/src/lagrangian/intermediate/parcels/Templates/KinematicParcel/KinematicParcel.C +++ b/src/lagrangian/intermediate/parcels/Templates/KinematicParcel/KinematicParcel.C @@ -275,7 +275,7 @@ bool Foam::KinematicParcel<ParcelType>::move const scalar maxCo = td.cloud().solution().maxCo(); scalar tEnd = (1.0 - p.stepFraction())*trackTime; - const scalar dtMax = tEnd; + const scalar dtMax = tEnd/td.cloud().solution().subCycles(); while (td.keepParticle && !td.switchProcessor && tEnd > ROOTVSMALL) { -- 1.7.10.4 |
|
0001-Add-subcycles-to-Lagrangian_v1.patch (3,988 bytes)
diff --git a/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolution.C b/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolution.C index fd7bf31..70da8f4 100644 --- a/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolution.C +++ b/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolution.C @@ -38,6 +38,7 @@ Foam::cloudSolution::cloudSolution dict_(dict), active_(dict.lookup("active")), transient_(false), + subCycles_(1), calcFrequency_(1), maxCo_(0.3), iter_(1), @@ -64,6 +65,7 @@ Foam::cloudSolution::cloudSolution dict_(cs.dict_), active_(cs.active_), transient_(cs.transient_), + subCycles_(cs.subCycles_), calcFrequency_(cs.calcFrequency_), maxCo_(cs.maxCo_), iter_(cs.iter_), @@ -85,6 +87,7 @@ Foam::cloudSolution::cloudSolution dict_(dictionary::null), active_(false), transient_(false), + subCycles_(1), calcFrequency_(0), maxCo_(GREAT), iter_(0), @@ -123,6 +126,12 @@ void Foam::cloudSolution::read() >> resetSourcesOnStartup_; } } + else + { + dict_.lookup("subCycles") >> subCycles_; + subCycles_ = max(subCycles_,1); +// dict_.lookupOrDefault<int>("subCycles",1) >> subCycles_; + } if (coupled_) { diff --git a/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolution.H b/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolution.H index e155abc..92596a8 100644 --- a/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolution.H +++ b/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolution.H @@ -65,6 +65,10 @@ class cloudSolution //- Transient flag Switch transient_; + //- Sub cycles - cloud steps per carrier step + // NOTE: Transient operation only + label subCycles_; + //- Calculation frequency - carrier steps per cloud step // NOTE: Steady operation only label calcFrequency_; @@ -156,6 +160,9 @@ public: //- Return const access to the steady flag inline const Switch steadyState() const; + //- Return const access to the sub cycles + inline label subCycles() const; + //- Return const access to the calculation frequency inline label calcFrequency() const; diff --git a/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolutionI.H b/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolutionI.H index 6280b97..ad9e64c 100644 --- a/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolutionI.H +++ b/src/lagrangian/intermediate/clouds/Templates/KinematicCloud/cloudSolution/cloudSolutionI.H @@ -71,6 +71,12 @@ inline const Foam::Switch Foam::cloudSolution::steadyState() const } +inline Foam::label Foam::cloudSolution::subCycles() const +{ + return subCycles_; +} + + inline Foam::label Foam::cloudSolution::calcFrequency() const { return calcFrequency_; diff --git a/src/lagrangian/intermediate/parcels/Templates/KinematicParcel/KinematicParcel.C b/src/lagrangian/intermediate/parcels/Templates/KinematicParcel/KinematicParcel.C index 7ec52b1..cbd3417 100644 --- a/src/lagrangian/intermediate/parcels/Templates/KinematicParcel/KinematicParcel.C +++ b/src/lagrangian/intermediate/parcels/Templates/KinematicParcel/KinematicParcel.C @@ -275,7 +275,7 @@ bool Foam::KinematicParcel<ParcelType>::move const scalar maxCo = td.cloud().solution().maxCo(); scalar tEnd = (1.0 - p.stepFraction())*trackTime; - const scalar dtMax = tEnd; + const scalar dtMax = tEnd/td.cloud().solution().subCycles(); while (td.keepParticle && !td.switchProcessor && tEnd > ROOTVSMALL) { |
|
Updated the patch to silence -Wignored-qualifiers warnings (i.e. removed to unnecessary 'const') |
|
I am looking into this patch but the equivalent functionality is already present in OpenFOAM-dev in the form of maxCo: const scalar maxCo = td.cloud().solution().maxCo(); scalar tEnd = (1.0 - p.stepFraction())*trackTime; scalar dtMax = trackTime; if (td.cloud().solution().transient()) { dtMax *= maxCo; } |
|
The max. Courant number definitely imposes a limiting timescales, however there may be cases where this is not sufficient. The Lagrangian timescale for fuel sprays is not only determined by the max. Courant number, but also by the momentum, heat and mass relaxation timescale. Also the droplet breakup timescale should be considered. In the dieselSpray implementation by Niklas Nordin (e.g. in OpenFOAM 2.0.x) the momentum, heat and mass relaxation timescale were considered together with the option of setting the a minimum number of sub-cycles: https://github.com/OpenFOAM/OpenFOAM-2.0.x/blob/master/src/lagrangian/dieselSpray/parcel/parcel.C#L155 In other Lagrangian spray solvers (e.g. Star-CD), the Lagrangian timescale is similarly determined as: dt_Lag = min(dt, tau_Co, tau_mom, tau_heat, tau_mass, 0.3*tau_breakup) To implement this in a similar way is a more extensive task and I understand that it might not be feasible to do this now (or at all). However, the Courant number approach, depends on the droplet velocity, thus my concern was that this approach might allow for larger time steps in cases where velocities are small but e.g. the heat relaxation timescale would set the limiting timescale. The min. sub-cycle parameter, would allow to limit in these cases the max. Lagrangian time-step independent of the velocity. I already discussed this back in 2013 with Andy Heather, but he refused to implement the sub-cycling as proposed in my patches (but he didn't want to close the bug report either). Personally, I don't need the sub-cycling any more, because my research interest is in LES of spray flames, which require very small time steps for the Eulerian phase already. Hence, this is mainly concerns unsteady RANS simulations where larger time steps may be used. |
|
I don't see much difference between the way the two approaches are implemented. In the case of sub-cycling you divide the dtMax by some number larger than 1 and in the maxCo you multiply dtMax by some number smaller than 1. Under what conditions will the behavior be different? I agree that the time-step should be limited by the set of physical time-scales as it was done in the dieselSpray library and I am not happy that the replacement library does not include ALL of that functionality and more at the time the dieselSpray library was removed. If you have patches to reintroduce the missing functionality I would be happy to apply them. |
|
Arrg, sorry I missed that part! Indeed the maxCo in OpenFOAM-dev limits the the Lagrangian time scale similarly as the sub-cycling does. (In my defense, this was differently implemented when I reported the bug (i.e. in OpenFOAM 2.2.x)). Hence, my patch is obsolete and this bug report can be closed. Regarding the missing functionality compared to the dieselSpray library: Unfortunately, I don't have patches for this and I am not intending to work on this (my research focus is nowadays more on combustion simulations). |
|
OK, thanks for your help and for all the excellent patches and improvements you have provided for OpenFOAM. Please keep contributing and I will endeavour to include them promptly in future. |
Date Modified | Username | Field | Change |
---|---|---|---|
2013-08-12 16:59 | dkxls | New Issue | |
2013-08-13 16:38 | dkxls | Tag Attached: Lagrangian | |
2013-08-13 16:38 | dkxls | Tag Attached: spray | |
2013-08-13 16:38 | dkxls | Tag Attached: sprayEngineFoam | |
2013-08-13 16:38 | dkxls | Tag Attached: sprayFoam | |
2013-08-13 19:50 | dkxls | File Added: 0001-Add-subcycles-to-Lagrangian.patch | |
2013-08-14 11:50 | dkxls | File Added: 0001-Add-subcycles-to-Lagrangian_v1.patch | |
2013-08-14 11:52 | dkxls | Note Added: 0002408 | |
2015-02-15 17:24 | wyldckat | Tag Attached: contribution | |
2016-02-02 21:34 | henry | Note Added: 0005886 | |
2016-02-03 12:47 | dkxls | Note Added: 0005892 | |
2016-02-03 12:59 | henry | Note Added: 0005893 | |
2016-02-03 13:13 | dkxls | Note Added: 0005895 | |
2016-02-03 13:20 | henry | Note Added: 0005896 | |
2016-02-03 13:21 | henry | Status | new => closed |
2016-02-03 13:21 | henry | Assigned To | => henry |
2016-02-03 13:21 | henry | Resolution | open => no change required |