1 /*---------------------------------------------------------------------------*\
3 \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
5 \\ / A nd | Copyright (C) 1991-2010 OpenCFD Ltd.
7 -------------------------------------------------------------------------------
9 This file is part of OpenFOAM.
11 OpenFOAM is free software: you can redistribute it and/or modify it
12 under the terms of the GNU General Public License as published by
13 the Free Software Foundation, either version 3 of the License, or
14 (at your option) any later version.
16 OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
17 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
18 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
21 You should have received a copy of the GNU General Public License
22 along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
24 \*---------------------------------------------------------------------------*/
26 #include "SCOPELaminarFlameSpeed.H"
27 #include "addToRunTimeSelectionTable.H"
29 // * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
33 namespace laminarFlameSpeedModels
35 defineTypeNameAndDebug(SCOPE, 0);
37 addToRunTimeSelectionTable
47 // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
49 Foam::laminarFlameSpeedModels::SCOPE::polynomial::polynomial
51 const dictionary& polyDict
54 FixedList<scalar, 7>(polyDict.lookup("coefficients")),
55 ll(readScalar(polyDict.lookup("lowerLimit"))),
56 ul(readScalar(polyDict.lookup("upperLimit"))),
57 llv(polyPhi(ll, *this)),
58 ulv(polyPhi(ul, *this)),
63 Foam::laminarFlameSpeedModels::SCOPE::SCOPE
65 const dictionary& dict,
66 const hhuCombustionThermo& ct
69 laminarFlameSpeed(dict, ct),
71 coeffsDict_(dict.subDict(typeName + "Coeffs").subDict(fuel_)),
72 LFL_(readScalar(coeffsDict_.lookup("lowerFlamabilityLimit"))),
73 UFL_(readScalar(coeffsDict_.lookup("upperFlamabilityLimit"))),
74 SuPolyL_(coeffsDict_.subDict("lowerSuPolynomial")),
75 SuPolyU_(coeffsDict_.subDict("upperSuPolynomial")),
76 Texp_(readScalar(coeffsDict_.lookup("Texp"))),
77 pexp_(readScalar(coeffsDict_.lookup("pexp"))),
78 MaPolyL_(coeffsDict_.subDict("lowerMaPolynomial")),
79 MaPolyU_(coeffsDict_.subDict("upperMaPolynomial"))
81 SuPolyL_.ll = max(SuPolyL_.ll, LFL_) + SMALL;
82 SuPolyU_.ul = min(SuPolyU_.ul, UFL_) - SMALL;
84 SuPolyL_.lu = 0.5*(SuPolyL_.ul + SuPolyU_.ll);
85 SuPolyU_.lu = SuPolyL_.lu - SMALL;
87 MaPolyL_.lu = 0.5*(MaPolyL_.ul + MaPolyU_.ll);
88 MaPolyU_.lu = MaPolyL_.lu - SMALL;
92 Info<< "phi Su (T = Tref, p = pref)" << endl;
94 for (int i=0; i<n; i++)
96 scalar phi = (2.0*i)/n;
97 Info<< phi << token::TAB << SuRef(phi) << endl;
103 // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * //
105 Foam::laminarFlameSpeedModels::SCOPE::~SCOPE()
109 // * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * * //
111 inline Foam::scalar Foam::laminarFlameSpeedModels::SCOPE::polyPhi
117 scalar x = phi - 1.0;
123 + x*(a[1] + x*(a[2] + x*(a[3] + x*(a[4] + x*(a[5] + x*a[6])))))
128 inline Foam::scalar Foam::laminarFlameSpeedModels::SCOPE::SuRef
133 if (phi < LFL_ || phi > UFL_)
135 // Return 0 beyond the flamibility limits
138 else if (phi < SuPolyL_.ll)
140 // Use linear interpolation between the low end of the
141 // lower polynomial and the lower flamibility limit
142 return SuPolyL_.llv*(phi - LFL_)/(SuPolyL_.ll - LFL_);
144 else if (phi > SuPolyU_.ul)
146 // Use linear interpolation between the upper end of the
147 // upper polynomial and the upper flamibility limit
148 return SuPolyU_.ulv*(UFL_ - phi)/(UFL_ - SuPolyU_.ul);
150 else if (phi < SuPolyL_.lu)
152 // Evaluate the lower polynomial
153 return polyPhi(phi, SuPolyL_);
155 else if (phi > SuPolyU_.lu)
157 // Evaluate the upper polynomial
158 return polyPhi(phi, SuPolyU_);
162 FatalErrorIn("laminarFlameSpeedModels::SCOPE::SuRef(scalar phi)")
164 << " cannot be handled by SCOPE function with the "
173 inline Foam::scalar Foam::laminarFlameSpeedModels::SCOPE::Ma
178 if (phi < MaPolyL_.ll)
180 // Beyond the lower limit assume Ma is constant
183 else if (phi > MaPolyU_.ul)
185 // Beyond the upper limit assume Ma is constant
188 else if (phi < SuPolyL_.lu)
190 // Evaluate the lower polynomial
191 return polyPhi(phi, MaPolyL_);
193 else if (phi > SuPolyU_.lu)
195 // Evaluate the upper polynomial
196 return polyPhi(phi, MaPolyU_);
200 FatalErrorIn("laminarFlameSpeedModels::SCOPE::Ma(scalar phi)")
202 << " cannot be handled by SCOPE function with the "
211 inline Foam::scalar Foam::laminarFlameSpeedModels::SCOPE::Su0pTphi
218 static const scalar Tref = 300.0;
219 static const scalar pRef = 1.013e5;
221 return SuRef(phi)*pow((Tu/Tref), Texp_)*pow((p/pRef), pexp_);
225 Foam::tmp<Foam::volScalarField> Foam::laminarFlameSpeedModels::SCOPE::Su0pTphi
227 const volScalarField& p,
228 const volScalarField& Tu,
232 tmp<volScalarField> tSu0
245 dimensionedScalar("Su0", dimVelocity, 0.0)
249 volScalarField& Su0 = tSu0();
253 Su0[celli] = Su0pTphi(p[celli], Tu[celli], phi);
256 forAll(Su0.boundaryField(), patchi)
258 scalarField& Su0p = Su0.boundaryField()[patchi];
259 const scalarField& pp = p.boundaryField()[patchi];
260 const scalarField& Tup = Tu.boundaryField()[patchi];
264 Su0p[facei] = Su0pTphi(pp[facei], Tup[facei], phi);
272 Foam::tmp<Foam::volScalarField> Foam::laminarFlameSpeedModels::SCOPE::Su0pTphi
274 const volScalarField& p,
275 const volScalarField& Tu,
276 const volScalarField& phi
279 tmp<volScalarField> tSu0
292 dimensionedScalar("Su0", dimVelocity, 0.0)
296 volScalarField& Su0 = tSu0();
300 Su0[celli] = Su0pTphi(p[celli], Tu[celli], phi[celli]);
303 forAll(Su0.boundaryField(), patchi)
305 scalarField& Su0p = Su0.boundaryField()[patchi];
306 const scalarField& pp = p.boundaryField()[patchi];
307 const scalarField& Tup = Tu.boundaryField()[patchi];
308 const scalarField& phip = phi.boundaryField()[patchi];
326 Foam::tmp<Foam::volScalarField> Foam::laminarFlameSpeedModels::SCOPE::Ma
328 const volScalarField& phi
331 tmp<volScalarField> tMa
338 phi.time().timeName(),
344 dimensionedScalar("Ma", dimless, 0.0)
348 volScalarField& ma = tMa();
352 ma[celli] = Ma(phi[celli]);
355 forAll(ma.boundaryField(), patchi)
357 scalarField& map = ma.boundaryField()[patchi];
358 const scalarField& phip = phi.boundaryField()[patchi];
362 map[facei] = Ma(phip[facei]);
370 Foam::tmp<Foam::volScalarField>
371 Foam::laminarFlameSpeedModels::SCOPE::Ma() const
373 if (hhuCombustionThermo_.composition().contains("ft"))
375 const volScalarField& ft = hhuCombustionThermo_.composition().Y("ft");
381 hhuCombustionThermo_.lookup("stoichiometricAirFuelMassRatio")
382 )*ft/(scalar(1) - ft)
387 const fvMesh& mesh = hhuCombustionThermo_.p().mesh();
389 return tmp<volScalarField>
396 mesh.time().timeName(),
402 dimensionedScalar("Ma", dimless, Ma(equivalenceRatio_))
409 Foam::tmp<Foam::volScalarField>
410 Foam::laminarFlameSpeedModels::SCOPE::operator()() const
412 if (hhuCombustionThermo_.composition().contains("ft"))
414 const volScalarField& ft = hhuCombustionThermo_.composition().Y("ft");
418 hhuCombustionThermo_.p(),
419 hhuCombustionThermo_.Tu(),
422 hhuCombustionThermo_.lookup("stoichiometricAirFuelMassRatio")
423 )*ft/(scalar(1) - ft)
430 hhuCombustionThermo_.p(),
431 hhuCombustionThermo_.Tu(),
438 // ************************************************************************* //