27 inline doublereal
Frot(doublereal tr, doublereal sqtr)
29 const doublereal c1 = 0.5*sqrt(
Pi)*
Pi;
30 const doublereal c2 = 0.25*
Pi*
Pi + 2.0;
31 const doublereal c3 = sqrt(
Pi)*
Pi;
32 return 1.0 + c1*sqtr + c2*tr + c3*sqtr*tr;
37 MultiTransport::MultiTransport(
thermo_t* thermo)
48 m_a.resize(3*
m_nsp, 1.0);
49 m_b.resize(3*
m_nsp, 0.0);
53 m_frot_298.resize(
m_nsp);
54 m_rotrelax.resize(
m_nsp);
56 m_cinternal.resize(
m_nsp);
66 m_lmatrix_soln_ok =
false;
68 m_thermal_tlast = 0.0;
71 m_spwork1.resize(
m_nsp);
72 m_spwork2.resize(
m_nsp);
73 m_spwork3.resize(
m_nsp);
78 for (
size_t i = 0; i <
m_nsp; i++) {
79 for (
size_t j = i; j <
m_nsp; j++) {
81 m_log_eps_k(j,i) = m_log_eps_k(i,j);
87 const doublereal sq298 = sqrt(298.0);
88 const doublereal kb298 =
Boltzmann * 298.0;
89 m_sqrt_eps_k.resize(m_nsp);
90 for (
size_t k = 0; k <
m_nsp; k++) {
92 m_frot_298[k] =
Frot(
m_eps[k]/kb298, m_sqrt_eps_k[k]/sq298);
98 solveLMatrixEquation();
100 for (
size_t k = 0; k < 2*
m_nsp; k++) {
108 solveLMatrixEquation();
110 for (
size_t k = 0; k <
m_nsp; k++) {
115 void MultiTransport::solveLMatrixEquation()
120 if (m_lmatrix_soln_ok) {
128 for (
size_t k = 0; k <
m_nsp; k++) {
147 for (
size_t k = 0; k <
m_nsp; k++) {
148 if (!hasInternalModes(k)) {
149 m_b[2*m_nsp + k] = 0.0;
154 m_Lmatrix.
resize(3*m_nsp, 3*m_nsp, 0.0);
171 copy(m_b.begin(), m_b.end(), m_a.begin());
174 }
catch (CanteraError& err) {
176 throw CanteraError(
"MultiTransport::solveLMatrixEquation",
177 "error in solving L matrix.");
179 m_lmatrix_soln_ok =
true;
186 size_t ldx,
const doublereal*
const grad_X,
187 size_t ldf, doublereal*
const fluxes)
195 bool addThermalDiffusion =
false;
196 for (
size_t i = 0; i < ndim; i++) {
197 if (grad_T[i] != 0.0) {
198 addThermalDiffusion =
true;
201 if (addThermalDiffusion) {
208 for (
size_t i = 0; i <
m_nsp; i++) {
210 for (
size_t j = 0; j <
m_nsp; j++) {
221 doublereal gradmax = -1.0;
222 for (
size_t j = 0; j <
m_nsp; j++) {
223 if (fabs(grad_X[j]) > gradmax) {
224 gradmax = fabs(grad_X[j]);
231 for (
size_t j = 0; j <
m_nsp; j++) {
235 for (
size_t n = 0; n < ldx*ndim; n++) {
240 const doublereal* gx;
241 for (
size_t n = 0; n < ndim; n++) {
243 copy(gx, gx + m_nsp, fluxes + ldf*n);
244 fluxes[jmax + n*ldf] = 0.0;
251 "Error factorizing matrix.");
253 info = m_aa.
solve(fluxes, ndim, ldf);
256 "Error solving linear system.");
260 doublereal pp = pressure_ig();
265 for (
size_t n = 0; n < ndim; n++) {
267 for (
size_t i = 0; i <
m_nsp; i++) {
268 fluxes[i + offset] *= rho * y[i] / pp;
273 if (addThermalDiffusion) {
274 for (
size_t n = 0; n < ndim; n++) {
276 doublereal grad_logt = grad_T[n]/
m_temp;
277 for (
size_t i = 0; i <
m_nsp; i++) {
278 fluxes[i + offset] -=
m_spwork[i]*grad_logt;
293 double t1 = state1[0];
298 double t2 = state2[0];
301 double p = 0.5*(p1 + p2);
302 double t = 0.5*(state1[0] + state2[0]);
304 for (n = 0; n < nsp; n++) {
305 x3[n] = 0.5*(x1[n] + x2[n]);
317 bool addThermalDiffusion =
false;
318 if (state1[0] != state2[0]) {
319 addThermalDiffusion =
true;
326 for (
size_t i = 0; i <
m_nsp; i++) {
327 doublereal sum = 0.0;
328 for (
size_t j = 0; j <
m_nsp; j++) {
339 doublereal gradmax = -1.0;
340 for (
size_t j = 0; j <
m_nsp; j++) {
341 if (fabs(x2[j] - x1[j]) > gradmax) {
342 gradmax = fabs(x1[j] - x2[j]);
350 for (
size_t j = 0; j <
m_nsp; j++) {
352 fluxes[j] = x2[j] - x1[j];
360 "Error in factorization. Info = "+
int2str(info));
362 info = m_aa.
solve(fluxes);
365 "Error in linear solve. Info = "+
int2str(info));
368 doublereal pp = pressure_ig();
372 for (
size_t i = 0; i <
m_nsp; i++) {
373 fluxes[i] *= rho * y[i] / pp;
377 if (addThermalDiffusion) {
378 doublereal grad_logt = (t2 - t1)/
m_temp;
379 for (
size_t i = 0; i <
m_nsp; i++) {
386 const doublereal*
const state2,
387 const doublereal delta,
388 doublereal*
const fluxes)
392 fluxes[k] /=
m_mw[k];
398 doublereal p = pressure_ig();
414 int ierr =
invert(m_Lmatrix, m_nsp);
416 throw CanteraError(
"MultiTransport::getMultiDiffCoeffs",
417 string(
" invert returned ierr = ")+
int2str(ierr));
420 m_lmatrix_soln_ok =
false;
422 doublereal prefactor = 16.0 *
m_temp
426 for (
size_t i = 0; i <
m_nsp; i++) {
427 for (
size_t j = 0; j <
m_nsp; j++) {
428 c = prefactor/
m_mw[j];
430 (m_Lmatrix(i,j) - m_Lmatrix(i,i));
441 GasTransport::update_T();
446 m_lmatrix_soln_ok =
false;
455 for (
size_t k = 0; k <
m_nsp; k++) {
462 m_lmatrix_soln_ok =
false;
479 for (
size_t i = 0; i <
m_nsp; i++) {
480 for (
size_t j = i; j <
m_nsp; j++) {
481 z =
m_logt - m_log_eps_k(i,j);
504 for (
size_t k = 0; k <
m_nsp; k++) {
507 m_rotrelax[k] = std::max(1.0,
m_zrot[k]) * m_frot_298[k]/
Frot(tr, sqtr);
512 for (
size_t k = 0; k <
m_nsp; k++) {
529 for (
size_t k = 0; k <
m_nsp; k++) {
530 m_cinternal[k] = cp[k] - 2.5;
539 bool MultiTransport::hasInternalModes(
size_t j)
546 doublereal prefactor = 16.0*
m_temp/25.0;
548 for (
size_t i = 0; i <
m_nsp; i++) {
553 for (
size_t k = 0; k <
m_nsp; k++) {
558 for (
size_t j = 0; j !=
m_nsp; ++j) {
559 m_Lmatrix(i,j) = prefactor * x[j]
563 m_Lmatrix(i,i) = 0.0;
569 doublereal prefactor = 1.6*
m_temp;
571 doublereal sum, wj, xj;
572 for (
size_t j = 0; j <
m_nsp; j++) {
576 for (
size_t i = 0; i <
m_nsp; i++) {
577 m_Lmatrix(i,j + m_nsp) = - prefactor * x[i] * xj *
m_mw[i] *
583 sum -= m_Lmatrix(i,j+m_nsp);
585 m_Lmatrix(j,j+m_nsp) += sum;
591 for (
size_t j = 0; j <
m_nsp; j++) {
592 for (
size_t i = 0; i <
m_nsp; i++) {
593 m_Lmatrix(i+m_nsp,j) = m_Lmatrix(j,i+m_nsp);
598 void MultiTransport::eval_L1010(
const doublereal* x)
600 const doublereal fiveover3pi = 5.0/(3.0*
Pi);
601 doublereal prefactor = (16.0*
m_temp)/25.0;
603 doublereal constant1, wjsq, constant2, constant3, constant4,
604 fourmj, threemjsq, sum, sumwij;;
605 doublereal term1, term2;
607 for (
size_t j = 0; j <
m_nsp; j++) {
611 constant1 = prefactor*x[j];
613 constant2 = 13.75*wjsq;
614 constant3 =
m_crot[j]/m_rotrelax[j];
615 constant4 = 7.5*wjsq;
616 fourmj = 4.0*m_mw[j];
617 threemjsq = 3.0*m_mw[j]*m_mw[j];
619 for (
size_t i = 0; i <
m_nsp; i++) {
621 sumwij = m_mw[i] + m_mw[j];
622 term1 =
m_bdiff(i,j) * sumwij*sumwij;
623 term2 = fourmj*
m_astar(i,j)*(1.0 + fiveover3pi*
625 (
m_crot[i]/m_rotrelax[i])));
627 m_Lmatrix(i+m_nsp,j+m_nsp) = constant1*x[i]*m_mw[i] /(m_mw[j]*term1) *
628 (constant2 - threemjsq*
m_bstar(i,j)
631 sum += x[i] /(term1) *
632 (constant4 + m_mw[i]*m_mw[i]*
633 (6.25 - 3.0*
m_bstar(i,j)) + term2*m_mw[i]);
636 m_Lmatrix(j+m_nsp,j+m_nsp) -= sum*constant1;
640 void MultiTransport::eval_L1001(
const doublereal* x)
642 doublereal prefactor = 32.00*
m_temp/(5.00*
Pi);
643 doublereal constant, sum;
646 for (
size_t j = 0; j <
m_nsp; j++) {
648 if (hasInternalModes(j)) {
649 constant = prefactor*m_mw[j]*x[j]*
m_crot[j]/(m_cinternal[j]*m_rotrelax[j]);
651 for (
size_t i = 0; i <
m_nsp; i++) {
653 m_Lmatrix(i+m_nsp,j+n2) = constant *
m_astar(j,i) * x[i] /
654 ((m_mw[j] + m_mw[i]) *
m_bdiff(j,i));
655 sum += m_Lmatrix(i+m_nsp,j+n2);
658 m_Lmatrix(j+m_nsp,j+n2) += sum;
660 for (
size_t i = 0; i <
m_nsp; i++) {
661 m_Lmatrix(i+m_nsp,j+n2) = 0.0;
667 void MultiTransport::eval_L0001()
670 for (
size_t j = 0; j <
m_nsp; j++) {
671 for (
size_t i = 0; i <
m_nsp; i++) {
672 m_Lmatrix(i,j+n2) = 0.0;
677 void MultiTransport::eval_L0100()
680 for (
size_t j = 0; j <
m_nsp; j++)
681 for (
size_t i = 0; i <
m_nsp; i++) {
682 m_Lmatrix(i+n2,j) = 0.0;
686 void MultiTransport::eval_L0110()
689 for (
size_t j = 0; j <
m_nsp; j++)
690 for (
size_t i = 0; i <
m_nsp; i++) {
691 m_Lmatrix(i+n2,j+m_nsp) = m_Lmatrix(j+m_nsp,i+n2);
695 void MultiTransport::eval_L0101(
const doublereal* x)
697 const doublereal fivepi = 5.00*
Pi;
698 const doublereal eightoverpi = 8.0 /
Pi;
700 doublereal prefactor = 4.00*
m_temp;
702 doublereal constant1, constant2, diff_int, sum;
703 for (
size_t i = 0; i <
m_nsp; i++) {
704 if (hasInternalModes(i)) {
706 constant1 = prefactor*x[i]/m_cinternal[i];
707 constant2 = 12.00*m_mw[i]*
m_crot[i] /
708 (fivepi*m_cinternal[i]*m_rotrelax[i]);
710 for (
size_t k = 0; k <
m_nsp; k++) {
713 m_Lmatrix(k+n2,i+n2) = 0.0;
714 sum += x[k]/diff_int;
715 if (k != i) sum += x[k]*
m_astar(i,k)*constant2 /
719 m_Lmatrix(i+n2,i+n2) =
720 - eightoverpi*m_mw[i]*x[i]*x[i]*
m_crot[i] /
724 for (
size_t k = 0; k <
m_nsp; k++) {
725 m_Lmatrix(i+n2,i+n2) = 1.0;
virtual doublereal thermalConductivity()
Returns the mixture thermal conductivity in W/m/K.
void eval_L1000()
Evaluate the L1000 matrices.
virtual void updateSpeciesViscosities()
Update the pure-species viscosities.
virtual doublereal density() const
Density (kg/m^3).
std::string int2str(const int n, const std::string &fmt)
Convert an int to a string using a format converter.
DenseMatrix m_bstar
Dense matrix for bstar.
int invert(DenseMatrix &A, size_t nn)
invert A. A is overwritten with A^-1.
void restoreState(const vector_fp &state)
Restore a state saved on a previous call to saveState.
virtual void getThermalDiffCoeffs(doublereal *const dt)
Return the thermal diffusion coefficients (kg/m/s)
virtual void setState_TPX(doublereal t, doublereal p, const doublereal *x)
Set the temperature (K), pressure (Pa), and mole fractions.
Interface for class MultiTransport.
DenseMatrix m_astar
Dense matrix for astar.
virtual void getMassFluxes(const doublereal *state1, const doublereal *state2, doublereal delta, doublereal *fluxes)
Get the mass diffusional fluxes [kg/m^2/s] of the species, given the thermodynamic state at two nearb...
thermo_t * m_thermo
pointer to the object representing the phase
DenseMatrix m_cstar
Dense matrix for cstar.
void update_T()
Update basic temperature-dependent quantities if the temperature has changed.
int solve(DenseMatrix &A, double *b, size_t nrhs, size_t ldb)
Solve Ax = b. Array b is overwritten on exit with x.
DenseMatrix m_bdiff
Matrix of binary diffusion coefficients at the reference pressure and the current temperature Size is...
void getMoleFractions(doublereal *const x) const
Get the species mole fraction vector.
doublereal m_temp
Current value of the temperature at which the properties in this object are calculated (Kelvin)...
std::vector< vector_fp > m_cstar_poly
Fit for cstar collision integral.
static const doublereal Min_C_Internal
Constant to compare dimensionless heat capacities against zero.
doublereal Frot(doublereal tr, doublereal sqtr)
The Parker temperature correction to the rotational collision number.
Base class for a phase with thermodynamic properties.
int m_mode
Type of the polynomial fits to temperature.
virtual void init(ThermoPhase *thermo, int mode=0, int log_level=0)
Initialize a transport manager.
R poly8(D x, R *c)
Templated evaluation of a polynomial of order 8.
void resize(size_t n, size_t m, doublereal v=0.0)
Resize the matrix.
std::vector< vector_fp > m_omega22_poly
Fit for omega22 collision integral.
ThermoPhase object for the ideal gas equation of state - workhorse for Cantera (see Thermodynamic Pro...
R poly6(D x, R *c)
Templated evaluation of a polynomial of order 6.
vector_fp m_molefracs_last
Mole fraction vector from last L-matrix evaluation.
virtual void updateDiff_T()
Update the binary diffusion coefficients.
virtual void init(thermo_t *thermo, int mode=0, int log_level=0)
Initialize a transport manager.
vector_fp m_visc
vector of species viscosities (kg /m /s).
virtual void getMolarFluxes(const doublereal *const state1, const doublereal *const state2, const doublereal delta, doublereal *const fluxes)
Get the molar diffusional fluxes [kmol/m^2/s] of the species, given the thermodynamic state at two ne...
vector_fp m_spwork
work space length = m_kk
int solve(doublereal *b, size_t nrhs=1, size_t ldb=0)
Solves the Ax = b system returning x in the b spot.
void eval_L0000(const doublereal *const x)
Evaluate the L0000 matrices.
const doublereal * massFractions() const
Return a const pointer to the mass fraction array.
virtual void getMultiDiffCoeffs(const size_t ld, doublereal *const d)
Return the Multicomponent diffusion coefficients. Units: [m^2/s].
std::vector< vector_fp > m_bstar_poly
Fit for bstar collision integral.
int factor()
Factors the A matrix, overwriting A.
std::vector< vector_fp > m_astar_poly
Fit for astar collision integral.
Base class for exceptions thrown by Cantera classes.
vector_fp m_eps
Lennard-Jones well-depth of the species in the current phase.
void updateThermal_T()
Update the temperature-dependent terms needed to compute the thermal conductivity and thermal diffusi...
std::vector< vector_int > m_poly
Indices for the (i,j) interaction in collision integral fits.
size_t nSpecies() const
Returns the number of species in the phase.
virtual doublereal pressure() const
Return the thermodynamic pressure (Pa).
vector_fp m_zrot
Rotational relaxation number for each species.
doublereal temperature() const
Temperature (K).
DenseMatrix m_epsilon
The effective well depth for (i,j) collisions.
vector_fp m_crot
Dimensionless rotational heat capacity of each species.
std::vector< double > vector_fp
Turn on the use of stl vectors for the basic array type within cantera Vector of doubles.
doublereal m_sqrt_t
current value of temperature to 1/2 power
const doublereal Tiny
Small number to compare differences of mole fractions against.
doublereal meanMolecularWeight() const
The mean molecular weight. Units: (kg/kmol)
const doublereal GasConstant
Universal Gas Constant. [J/kmol/K].
Contains declarations for string manipulation functions within Cantera.
#define DATA_PTR(vec)
Creates a pointer to the start of the raw data for a vector.
virtual void getSpeciesFluxes(size_t ndim, const doublereal *const grad_T, size_t ldx, const doublereal *const grad_X, size_t ldf, doublereal *const fluxes)
Get the species diffusive mass fluxes wrt to the mass averaged velocity, given the gradients in mole ...
size_t m_nsp
Number of species.
doublereal m_logt
Current value of the log of the temperature.
bool m_abc_ok
Boolean indicating viscosity is up to date.
virtual void getCp_R_ref(doublereal *cprt) const
Returns the vector of nondimensional constant pressure heat capacities of the reference state at the ...
doublereal m_kbt
Current value of Boltzmann constant times the temperature (Joules)
void eval_L0010(const doublereal *const x)
Evaluate the L0010 matrices.
const doublereal Boltzmann
Boltzmann's constant [J/K].
DenseMatrix m_om22
Dense matrix for omega22.
vector_fp m_molefracs
Vector of species mole fractions.
Class GasTransport implements some functions and properties that are shared by the MixTransport and M...
void update_C()
Update basic concentration-dependent quantities if the concentrations have changed.
vector_fp m_mw
Local copy of the species molecular weights.