36 SpeciesThermoFactory* SpeciesThermoFactory::s_factory = 0;
37 mutex_t SpeciesThermoFactory::species_thermo_mutex;
54 int& has_nasa,
int& has_shomate,
int& has_simple,
57 size_t ns = spDataNodeList.size();
58 for (
size_t n = 0; n < ns; n++) {
59 XML_Node* spNode = spDataNodeList[n];
60 if (spNode->
hasChild(
"standardState")) {
62 string mname = ss[
"model"];
63 if (mname ==
"water" || mname ==
"waterIAPWS") {
76 }
else if (th.
hasChild(
"const_cp")) {
79 if (th.
child(
"poly")[
"order"] ==
"1") {
82 "poly with order > 1 not yet supported");
87 }
else if (th.
hasChild(
"NASA9MULTITEMP")) {
89 }
else if (th.
hasChild(
"adsorbate")) {
98 spNode->
attrib(
"name") +
" is missing the thermo XML node");
114 ScopedLock lock(species_thermo_mutex);
121 void SpeciesThermoFactory::deleteFactory()
123 ScopedLock lock(species_thermo_mutex);
130 SpeciesThermo* SpeciesThermoFactory::newSpeciesThermo(std::vector<XML_Node*> & spDataNodeList)
const
132 int inasa = 0, ishomate = 0, isimple = 0, iother = 0;
143 return newSpeciesThermo(
NASA*inasa
169 SpeciesThermo* SpeciesThermoFactory::newSpeciesThermoManager(std::string& stype)
const
172 if (ltype ==
"nasa") {
174 }
else if (ltype ==
"shomate") {
176 }
else if (ltype ==
"simple" || ltype ==
"constant_cp") {
178 }
else if (ltype ==
"nasa_shomate_duo") {
180 }
else if (ltype ==
"nasa_simple_duo") {
182 }
else if (ltype ==
"shomate_simple_duo") {
184 }
else if (ltype ==
"general") {
186 }
else if (ltype ==
"") {
209 doublereal tmin0, tmax0, tmin1, tmax1, tmin, tmid, tmax;
214 bool dualRange =
false;
235 tmax1 = tmin1 + 0.0001;
237 tmin1 =
fpValue((*f1ptr)[
"Tmin"]);
238 tmax1 =
fpValue((*f1ptr)[
"Tmax"]);
242 if (fabs(tmax0 - tmin1) < 0.01) {
253 copy(c0.begin(), c0.end(), c1.begin());
255 }
else if (fabs(tmax1 - tmin0) < 0.01) {
264 "non-continuous temperature ranges.");
274 copy(c0.begin(), c0.begin()+5, c.begin() + 3);
277 copy(c1.begin(), c1.begin()+5, c.begin() + 10);
278 sp.
install(speciesName, k,
NASA, &c[0], tmin, tmax, p0);
290 throw CanteraError(
"PDSS_HKFT::LookupGe",
"element " + elemName +
" not found");
295 "element " + elemName +
" does not have a supplied entropy298");
297 geValue *= (-298.15);
318 doublereal totalSum = 0.0;
319 for (
size_t m = 0; m < ne; m++) {
320 na = th_ptr->
nAtoms(k, m);
348 std::string astring = (*MinEQ3node)[
"Tmin"];
350 astring = (*MinEQ3node)[
"Tmax"];
352 astring = (*MinEQ3node)[
"Pref"];
355 doublereal deltaG_formation_pr_tr =
357 doublereal deltaH_formation_pr_tr =
363 doublereal dg = deltaG_formation_pr_tr * 4.184 * 1.0E3;
365 doublereal Mu0_tr_pr = fac + dg;
366 doublereal e = Entrop_pr_tr * 1.0E3 * 4.184;
367 doublereal Hcalc = Mu0_tr_pr + 298.15 * e;
368 doublereal DHjmol = deltaH_formation_pr_tr * 1.0E3 * 4.184;
372 if (fabs(Hcalc -DHjmol) > 10.* 1.0E6 * 4.184) {
373 throw CanteraError(
"installMinEQ3asShomateThermoFromXML()",
374 "DHjmol is not consistent with G and S" +
388 double As = a * 4.184;
389 double Bs = b * 4.184 * 1000.;
392 double Es = c * 4.184 / (1.0E6);
394 double t = 298.15 / 1000.;
395 double H298smFs = As * t + Bs * t * t / 2.0 - Es / t;
397 double HcalcS = Hcalc / 1.0E6;
398 double Fs = HcalcS - H298smFs;
400 double S298smGs = As * log(t) + Bs * t - Es/(2.0*t*t);
401 double ScalcS = e / 1.0E3;
402 double Gs = ScalcS - S298smGs;
412 coef[0] = tmax0 - 0.001;
413 copy(c0.begin(), c0.begin()+7, coef.begin() + 1);
414 copy(c0.begin(), c0.begin()+7, coef.begin() + 8);
431 doublereal tmin0, tmax0, tmin1, tmax1, tmin, tmid, tmax;
433 bool dualRange =
false;
450 tmax1 = tmin1 + 0.0001;
452 tmin1 =
fpValue((*f1ptr)[
"Tmin"]);
453 tmax1 =
fpValue((*f1ptr)[
"Tmax"]);
457 if (fabs(tmax0 - tmin1) < 0.01) {
468 "Shomate thermo requires 7 coefficients in float array.");
471 copy(c0.begin(), c0.begin()+7, c1.begin());
473 }
else if (fabs(tmax1 - tmin0) < 0.01) {
481 "non-continuous temperature ranges.");
483 if(c0.size() != 7 || c1.size() != 7)
486 "Shomate thermo requires 7 coefficients in float array.");
490 copy(c0.begin(), c0.begin()+7, c.begin() + 1);
491 copy(c1.begin(), c1.begin()+7, c.begin() + 8);
508 doublereal tmin, tmax;
536 const std::vector<XML_Node*>& tp)
542 std::vector<Nasa9Poly1*> regionPtrs;
543 doublereal tmin, tmax, pref =
OneAtm;
545 for (
size_t i = 0; i < tp.size(); i++) {
548 if (fptr->
name() ==
"NASA9") {
551 tmin =
fpValue((*fptr)[
"Tmin"]);
552 tmax =
fpValue((*fptr)[
"Tmax"]);
553 if ((*fptr).hasAttrib(
"P0")) {
556 if ((*fptr).hasAttrib(
"Pref")) {
557 pref =
fpValue((*fptr)[
"Pref"]);
561 if (cPoly.size() != 9) {
563 "Expected 9 coeff polynomial");
567 regionPtrs.push_back(np_ptr);
576 }
else if (nRegions == 1) {
590 const std::vector<XML_Node*>& tp)
593 int nRegTmp = tp.size();
595 std::vector<StatMech*> regionPtrs;
596 doublereal tmin, tmax = 0.0, pref =
OneAtm;
599 for (
int i = 0; i < nRegTmp; i++) {
602 if (fptr->
name() ==
"StatMech") {
605 tmin =
fpValue((*fptr)[
"Tmin"]);
606 tmax =
fpValue((*fptr)[
"Tmax"]);
607 if ((*fptr).hasAttrib(
"P0")) {
610 if ((*fptr).hasAttrib(
"Pref")) {
611 pref =
fpValue((*fptr)[
"Pref"]);
615 if (cPoly.size() != 0) {
617 "Expected no coeff: this is not a polynomial representation");
627 (&sp)->install(speciesName, k,
STAT, &coeffs[0], tmin, tmax, pref);
644 doublereal tmin, tmax, pref =
OneAtm;
660 nfreq = freqs.size();
662 for (
size_t n = 0; n < nfreq; n++) {
666 coeffs[0] =
static_cast<double>(nfreq);
667 coeffs[1] =
getFloat(f,
"binding_energy",
"toSI");
668 copy(freqs.begin(), freqs.end(), coeffs.begin() + 2);
669 (&sp)->install(speciesName, k,
ADSORBATE, &coeffs[0], tmin, tmax, pref);
672 void SpeciesThermoFactory::installThermoForSpecies
680 if (!(speciesNode.
hasChild(
"thermo"))) {
682 speciesNode[
"name"],
"<nonexistent>");
689 const std::vector<XML_Node*>& tpWC = thermo.
children();
690 std::vector<XML_Node*> tp;
691 for (
int i = 0; i < static_cast<int>(tpWC.size()); i++) {
692 if (!(tpWC[i])->isComment()) {
693 tp.push_back(tpWC[i]);
696 int nc =
static_cast<int>(tp.size());
697 string mname = thermo[
"model"];
699 if (mname ==
"MineralEQ3") {
701 if (f->
name() !=
"MinEQ3") {
702 throw CanteraError(
"SpeciesThermoFactory::installThermoForSpecies",
703 "confused: expedted MinEQ3");
709 if (f->
name() ==
"Shomate") {
711 }
else if (f->
name() ==
"const_cp") {
713 }
else if (f->
name() ==
"NASA") {
715 }
else if (f->
name() ==
"Mu0") {
717 }
else if (f->
name() ==
"NASA9") {
719 }
else if (f->
name() ==
"StatMech") {
721 }
else if (f->
name() ==
"adsorbate") {
725 speciesNode[
"name"], f->
name());
727 }
else if (nc == 2) {
730 if (f0->
name() ==
"NASA" && f1->
name() ==
"NASA") {
732 }
else if (f0->
name() ==
"Shomate" && f1->
name() ==
"Shomate") {
734 }
else if (f0->
name() ==
"StatMech") {
736 }
else if (f0->
name() ==
"NASA9" && f1->
name() ==
"NASA9") {
744 if (f0->
name() ==
"NASA9") {
746 }
else if (f0->
name() ==
"StatMech") {
759 void SpeciesThermoFactory::
760 installVPThermoForSpecies(
size_t k,
const XML_Node& speciesNode,
764 const XML_Node* phaseNode_ptr)
const
775 vp_ptr->createInstallPDSS(k, speciesNode, phaseNode_ptr);
781 f = SpeciesThermoFactory::factory();
790 f = SpeciesThermoFactory::factory();
799 f = SpeciesThermoFactory::factory();
static void installShomateThermoFromXML(const std::string &speciesName, SpeciesThermo &sp, size_t k, const XML_Node *f0ptr, const XML_Node *f1ptr)
Install a Shomate polynomial thermodynamic property parameterization for species k into a SpeciesTher...
Factory to build instances of classes that manage the standard-state thermodynamic properties of a se...
doublereal fpValue(const std::string &val)
Translate a string into one doublereal value.
doublereal nAtoms(size_t k, size_t m) const
Number of atoms of element m in species k.
Header for a single-species standard state object derived from SpeciesThermoInterpType based on a pie...
#define NASA
Two regions of 7 coefficient NASA Polynomials This is implemented in the class NasaPoly2 in NasaPoly2...
static void installAdsorbateThermoFromXML(const std::string &speciesName, SpeciesThermo &sp, size_t k, const XML_Node &f)
Install a Adsorbate polynomial thermodynamic property parameterization for species k into a SpeciesTh...
CTML ("Cantera Markup Language") is the variant of XML that Cantera uses to store data...
void popError()
Discard the last error message.
#define SHOMATE
Two regions of Shomate Polynomials.
Header for a single-species standard state object derived from SpeciesThermoInterpType based on the N...
size_t nElements() const
Number of elements.
const doublereal OneAtm
One atmosphere [Pa].
std::string attrib(const std::string &attr) const
Function returns the value of an attribute.
const std::vector< XML_Node * > & children() const
Return an unchangeable reference to the vector of children of the current node.
Virtual base class for the classes that manage the calculation of standard state properties for all t...
Declaration file for a virtual base class that manages the calculation of standard state properties f...
const size_t npos
index returned by functions to indicate "no position"
Header for the SimpleThermo (constant heat capacity) species reference-state model for multiple speci...
Header for a single-species standard state object derived from SpeciesThermoInterpType based on the N...
static void installNasa9ThermoFromXML(const std::string &speciesName, SpeciesThermo &sp, size_t k, const std::vector< XML_Node * > &tp)
Install a NASA9 polynomial thermodynamic property parameterization for species k into a SpeciesThermo...
virtual void install(const std::string &name, size_t index, int type, const doublereal *c, doublereal minTemp, doublereal maxTemp, doublereal refPressure)=0
Install a new species thermodynamic property parameterization for one species.
Class XML_Node is a tree-based representation of the contents of an XML file.
Virtual base class for the calculation of multiple-species thermodynamic reference-state property man...
doublereal getFloat(const Cantera::XML_Node &parent, const std::string &name, const std::string &type)
Get a floating-point value from a child element.
A species thermodynamic property manager for the NASA polynomial parameterization with two temperatur...
std::string lowercase(const std::string &s)
Cast a copy of a string to lower case.
void installMu0ThermoFromXML(const std::string &speciesName, SpeciesThermo &sp, size_t k, const XML_Node *Mu0Node_ptr)
Install a Mu0 polynomial thermodynamic reference state.
Pure Virtual base class for the species thermo manager classes.
XML_Node & child(const size_t n) const
Return a changeable reference to the n'th child of the current node.
doublereal entropyElement298(size_t m) const
Entropy of the element in its standard state at 298 K and 1 bar.
Base class for a phase with thermodynamic properties.
Contains const definitions for types of species reference-state thermodynamics managers (see Species ...
static void getSpeciesThermoTypes(std::vector< XML_Node * > &spDataNodeList, int &has_nasa, int &has_shomate, int &has_simple, int &has_other)
Examine the types of species thermo parameterizations, and return a flag indicating the type of refer...
SpeciesThermo * newSpeciesThermoMgr(std::vector< XML_Node * > spData_nodes, SpeciesThermoFactory *f)
Function to return SpeciesThermo manager.
static doublereal LookupGe(const std::string &elemName, ThermoPhase *th_ptr)
Look up the elemental reference state entropies.
A species thermodynamic property manager for a phase.
static void installNasaThermoFromXML(const std::string &speciesName, SpeciesThermo &sp, size_t k, const XML_Node *f0ptr, const XML_Node *f1ptr)
Install a NASA polynomial thermodynamic property parameterization for species k into a SpeciesThermo ...
virtual void install_STIT(SpeciesThermoInterpType *stit_ptr)=0
Install a new species thermodynamic property parameterization for one species.
static doublereal convertDGFormation(size_t k, ThermoPhase *th_ptr)
Convert delta G formulation.
std::string fp2str(const double x, const std::string &fmt)
Convert a double into a c++ string.
std::string name() const
Returns the name of the XML node.
Classes providing support for XML data files.
static void installStatMechThermoFromXML(const std::string &speciesName, SpeciesThermo &sp, int k, const std::vector< XML_Node * > &tp)
Install a stat mech based property solver for species k into a SpeciesThermo instance.
Header for the 2 regime 7 coefficient Nasa thermodynamic polynomials for multiple species in a phase...
Base class for exceptions thrown by Cantera classes.
This is a filter class for ThermoPhase that implements some prepatory steps for efficiently handling ...
#define SIMPLE
Constant Cp thermo.
bool hasChild(const std::string &ch) const
Tests whether the current node has a child node with a particular name.
SpeciesThermo * newSpeciesThermo(int type) const
Create a new species property manager for the reference state.
SpeciesThermo * newSpeciesThermoManager(std::string &stype) const
Create a new species thermo property manager given a string.
Header for a single-species standard state object derived from.
static void installMinEQ3asShomateThermoFromXML(const std::string &speciesName, ThermoPhase *th_ptr, SpeciesThermo &sp, size_t k, const XML_Node *MinEQ3node)
Install a NASA96 polynomial thermodynamic property parameterization for species k into a SpeciesTherm...
This species thermo manager requires that all species have one of two parameterizations.
#define ENTROPY298_UNKNOWN
Number indicating we don't know the entropy of the element in its most stable state at 298...
This file contains descriptions of templated subclasses of the virtual base class, SpeciesThermo, which includes SpeciesThermoDuo (see Managers for Calculating Reference-State Thermodynamics and class SpeciesThermoDuo)
Throw a named error for an unknown or missing species thermo model.
static void installSimpleThermoFromXML(const std::string &speciesName, SpeciesThermo &sp, size_t k, const XML_Node &f)
Install a Simple thermodynamic property parameterization for species k into a SpeciesThermo instance...
Header for factory to build instances of classes that manage the standard-state thermodynamic propert...
doublereal getFloatDefaultUnits(const Cantera::XML_Node &parent, const std::string &name, const std::string &defaultUnits, const std::string &type)
Get a floating-point value from a child element with a defined units field.
Headers for a completely general species thermodynamic property manager for a phase (see Managers for...
Header for the 2 regions Shomate polynomial for multiple species in a phase, derived from the Species...
A species thermodynamic property manager for the Shomate polynomial parameterization.
Header file for a derived class of ThermoPhase that handles variable pressure standard state methods ...
std::vector< double > vector_fp
Turn on the use of stl vectors for the basic array type within cantera Vector of doubles.
Unknown species thermo manager string error.
size_t elementIndex(const std::string &name) const
Return the index of element named 'name'.
#define STAT
Properties derived from theoretical considerations This is implemented in the class statmech in StatM...
#define DATA_PTR(vec)
Creates a pointer to the start of the raw data for a vector.
The NASA 9 polynomial parameterization for one temperature range.
std::string elementName(size_t m) const
Name of the element with index m.
Header for a single-species standard state object derived from SpeciesThermoInterpType based on the e...
The NASA 9 polynomial parameterization for a single species encompassing multiple temperature regions...
doublereal strSItoDbl(const std::string &strSI)
Interpret one or two token string as a single double.
size_t getFloatArray(const Cantera::XML_Node &node, std::vector< doublereal > &v, const bool convert, const std::string &unitsString, const std::string &nodeName)
This function reads the current node or a child node of the current node with the default name...
bool hasAttrib(const std::string &a) const
Tests whether the current node has an attribute with a particular name.
#define ADSORBATE
Surface Adsorbate Model for a species on a surface.