36 return ARRHENIUS_REACTION_RATECOEFF_TYPE;
48 m_b(rdata.rateCoeffParameters[1]),
49 m_E(rdata.rateCoeffParameters[2]),
50 m_A(rdata.rateCoeffParameters[0]) {
54 m_logA = std::log(m_A);
64 Arrhenius(doublereal A, doublereal b, doublereal E) :
91 doublereal
update(doublereal logT, doublereal recipT)
const {
92 return m_logA + m_b*logT - m_E*recipT;
102 doublereal
updateRC(doublereal logT, doublereal recipT)
const {
103 return m_A * std::exp(m_b*logT - m_E*recipT);
107 void writeUpdateRHS(std::ostream& s)
const {
108 s <<
" exp(" << m_logA;
110 s <<
" + " << m_b <<
" * tlog";
113 s <<
" - " << m_E <<
" * rt";
115 s <<
");" << std::endl;
118 doublereal activationEnergy_R()
const {
122 static bool alwaysComputeRate() {
127 doublereal m_logA, m_b, m_E, m_A;
150 return SURF_ARRHENIUS_REACTION_RATECOEFF_TYPE;
177 m_logA = std::log(m_A);
181 if (data.size() >= 7) {
182 for (
size_t n = 3; n < data.size()-3; n += 4) {
183 addCoverageDependence(
size_t(data[n]), data[n+1],
184 data[n+2], data[n+3]);
189 void addCoverageDependence(
size_t k, doublereal a,
190 doublereal m, doublereal e) {
202 void update_C(
const doublereal* theta) {
208 for (
size_t n = 0; n < m_ncov; n++) {
210 m_acov += m_ac[n] * theta[k];
211 m_ecov += m_ec[n] * theta[k];
213 for (
size_t n = 0; n < m_nmcov; n++) {
216 th = std::max(theta[k],
Tiny);
218 m_mcov += m_mc[n]*std::log(th);
228 doublereal
update(doublereal logT, doublereal recipT)
const {
229 return m_logA + m_acov + m_b*logT
230 - (m_E + m_ecov)*recipT + m_mcov;
240 doublereal
updateRC(doublereal logT, doublereal recipT)
const {
241 return m_A * std::exp(m_acov + m_b*logT - (m_E + m_ecov)*recipT + m_mcov);
244 doublereal activationEnergy_R()
const {
248 static bool alwaysComputeRate() {
253 doublereal m_logA, m_b, m_E, m_A;
254 doublereal m_acov, m_ecov, m_mcov;
255 std::vector<size_t> m_sp, m_msp;
257 size_t m_ncov, m_nmcov;
276 return EXCHANGE_CURRENT_REACTION_RATECOEFF_TYPE;
288 m_b(rdata.rateCoeffParameters[1]),
289 m_E(rdata.rateCoeffParameters[2]),
290 m_A(rdata.rateCoeffParameters[0]) {
294 m_logA = std::log(m_A);
311 m_logA = std::log(m_A);
331 doublereal
update(doublereal logT, doublereal recipT)
const {
332 return m_logA + m_b*logT - m_E*recipT;
342 doublereal
updateRC(doublereal logT, doublereal recipT)
const {
343 return m_A * std::exp(m_b*logT - m_E*recipT);
346 void writeUpdateRHS(std::ostream& s)
const {
347 s <<
" exp(" << m_logA;
349 s <<
" + " << m_b <<
" * tlog";
352 s <<
" - " << m_E <<
" * rt";
354 s <<
");" << std::endl;
357 doublereal activationEnergy_R()
const {
361 static bool alwaysComputeRate() {
366 doublereal m_logA, m_b, m_E, m_A;
375 return PLOG_REACTION_RATECOEFF_TYPE;
382 explicit Plog(
const ReactionData& rdata) :
386 typedef std::multimap<double, vector_fp>::const_iterator iter_t;
389 size_t rateCount = 0;
391 for (iter_t iter = rdata.plogParameters.begin();
392 iter != rdata.plogParameters.end();
394 double logp = std::log(iter->first);
395 if (pressures_.empty() || pressures_.rbegin()->first != logp) {
397 pressures_[logp] = std::make_pair(j, j+1);
401 pressures_[logp].second = j+1;
404 maxRates_ = std::max(rateCount, maxRates_);
407 A_.push_back(iter->second[0]);
408 n_.push_back(iter->second[1]);
409 Ea_.push_back(iter->second[2]);
414 for (pressureIter iter = pressures_.begin();
415 iter != pressures_.end();
417 if (iter->second.first == iter->second.second - 1) {
418 A_[iter->second.first] = std::log(A_[iter->second.first]);
423 pressures_.insert(std::make_pair(-1000.0, pressures_.begin()->second));
424 pressures_.insert(std::make_pair(1000.0, pressures_.rbegin()->second));
427 A1_.resize(maxRates_);
428 A2_.resize(maxRates_);
429 n1_.resize(maxRates_);
430 n2_.resize(maxRates_);
431 Ea1_.resize(maxRates_);
432 Ea2_.resize(maxRates_);
434 if (rdata.validate) {
441 void update_C(
const doublereal* c) {
443 if (logP_ > logP1_ && logP_ < logP2_) {
447 pressureIter iter = pressures_.upper_bound(c[0]);
449 "Pressure out of range: " +
fp2str(logP_));
451 "Pressure out of range: " +
fp2str(logP_));
454 logP2_ = iter->first;
455 size_t start = iter->second.first;
456 m2_ = iter->second.second - start;
457 for (
size_t m = 0; m < m2_; m++) {
458 A2_[m] = A_[start+m];
459 n2_[m] = n_[start+m];
460 Ea2_[m] = Ea_[start+m];
464 logP1_ = (--iter)->first;
465 start = iter->second.first;
466 m1_ = iter->second.second - start;
467 for (
size_t m = 0; m < m1_; m++) {
468 A1_[m] = A_[start+m];
469 n1_[m] = n_[start+m];
470 Ea1_[m] = Ea_[start+m];
473 rDeltaP_ = 1.0 / (logP2_ - logP1_);
479 doublereal update(doublereal logT, doublereal recipT)
const {
480 double log_k1, log_k2;
482 log_k1 = A1_[0] + n1_[0] * logT - Ea1_[0] * recipT;
485 for (
size_t m = 0; m < m1_; m++) {
486 k += A1_[m] * std::exp(n1_[m] * logT - Ea1_[m] * recipT);
488 log_k1 = std::log(k);
492 log_k2 = A2_[0] + n2_[0] * logT - Ea2_[0] * recipT;
495 for (
size_t m = 0; m < m2_; m++) {
496 k += A2_[m] * std::exp(n2_[m] * logT - Ea2_[m] * recipT);
498 log_k2 = std::log(k);
501 return log_k1 + (log_k2 - log_k1) * (logP_ - logP1_) * rDeltaP_;
509 doublereal updateRC(doublereal logT, doublereal recipT)
const {
510 return std::exp(update(logT, recipT));
513 doublereal activationEnergy_R()
const {
514 throw CanteraError(
"Plog::activationEnergy_R",
"Not implemented");
517 static bool alwaysComputeRate() {
525 void validate(
const ReactionData& rdata) {
526 double T[] = {1.0, 10.0, 100.0, 1000.0, 10000.0};
527 for (pressureIter iter = pressures_.begin();
530 update_C(&iter->first);
531 for (
size_t i=0; i < 5; i++) {
532 double k = updateRC(log(T[i]), 1.0/T[i]);
537 throw CanteraError(
"Plog::validate",
538 "Invalid rate coefficient for reaction #" +
539 int2str(rdata.number) +
":\n" + rdata.equation +
"\n" +
540 "at P = " +
fp2str(std::exp((++iter)->first)) +
549 std::map<double, std::pair<size_t, size_t> > pressures_;
550 typedef std::map<double, std::pair<size_t, size_t> >::iterator pressureIter;
557 double logP1_, logP2_;
578 return CHEBYSHEV_REACTION_RATECOEFF_TYPE;
585 explicit ChebyshevRate(
const ReactionData& rdata) :
586 nP_(rdata.chebDegreeP),
587 nT_(rdata.chebDegreeT),
588 chebCoeffs_(rdata.chebCoeffs),
589 dotProd_(rdata.chebDegreeT) {
590 double logPmin = std::log10(rdata.chebPmin);
591 double logPmax = std::log10(rdata.chebPmax);
592 double TminInv = 1.0 / rdata.chebTmin;
593 double TmaxInv = 1.0 / rdata.chebTmax;
595 TrNum_ = - TminInv - TmaxInv;
596 TrDen_ = 1.0 / (TmaxInv - TminInv);
597 PrNum_ = - logPmin - logPmax;
598 PrDen_ = 1.0 / (logPmax - logPmin);
603 void update_C(
const doublereal* c) {
604 double Pr = (2 * c[0] + PrNum_) * PrDen_;
608 for (
size_t j = 0; j < nT_; j++) {
609 dotProd_[j] = chebCoeffs_[nP_*j] + Pr * chebCoeffs_[nP_*j+1];
611 for (
size_t i = 2; i < nP_; i++) {
612 Cnp1 = 2 * Pr * Cn - Cnm1;
613 for (
size_t j = 0; j < nT_; j++) {
614 dotProd_[j] += Cnp1 * chebCoeffs_[nP_*j + i];
624 doublereal update(doublereal logT, doublereal recipT)
const {
625 double Tr = (2 * recipT + TrNum_) * TrDen_;
629 double logk = dotProd_[0] + Tr * dotProd_[1];
630 for (
size_t i = 2; i < nT_; i++) {
631 Cnp1 = 2 * Tr * Cn - Cnm1;
632 logk += Cnp1 * dotProd_[i];
644 doublereal updateRC(doublereal logT, doublereal recipT)
const {
645 return std::pow(10, update(logT, recipT));
648 doublereal activationEnergy_R()
const {
652 static bool alwaysComputeRate() {
657 double TrNum_, TrDen_;
658 double PrNum_, PrDen_;
void update_C(const doublereal *c)
Update concentration-dependent parts of the rate coefficient.
std::string int2str(const int n, const std::string &fmt)
Convert an int to a string using a format converter.
doublereal update(doublereal logT, doublereal recipT) const
Update the value of the logarithm of the rate constant.
vector_fp rateCoeffParameters
Vector of rate coefficient parameters.
Arrhenius()
Default constructor.
doublereal updateRC(doublereal logT, doublereal recipT) const
Update the value the rate constant.
#define AssertThrowMsg(expr, procedure, message)
Assertion must be true or an error is thrown.
static int type()
return the rate coefficient type.
doublereal updateRC(doublereal logT, doublereal recipT) const
Update the value the rate constant.
ExchangeCurrent(doublereal A, doublereal b, doublereal E)
Constructor.
void update_C(const doublereal *c)
Update concentration-dependent parts of the rate coefficient.
std::string fp2str(const double x, const std::string &fmt)
Convert a double into a c++ string.
Arrhenius reaction rate type depends only on temperature.
This file defines some constants used to specify reaction types.
Intermediate class which stores data about a reaction and its rate parameterization before adding the...
Arrhenius reaction rate type depends only on temperature.
Arrhenius(doublereal A, doublereal b, doublereal E)
Constructor.
doublereal update(doublereal logT, doublereal recipT) const
Update the value of the logarithm of the rate constant.
std::vector< double > vector_fp
Turn on the use of stl vectors for the basic array type within cantera Vector of doubles.
const doublereal Tiny
Small number to compare differences of mole fractions against.
doublereal updateRC(doublereal logT, doublereal recipT) const
Update the value the rate constant.
Contains declarations for string manipulation functions within Cantera.
ExchangeCurrent(const ReactionData &rdata)
Constructor with Arrhenius parameters from a ReactionData struct.
ExchangeCurrent()
Default constructor.
Arrhenius(const ReactionData &rdata)
Constructor from ReactionData.
An Arrhenius rate with coverage-dependent terms.
static int type()
return the rate coefficient type.
Definitions for the classes that are thrown when Cantera experiences an error condition (also contain...
doublereal update(doublereal logT, doublereal recipT) const
Update the value of the logarithm of the rate constant.