Cantera  2.0
VPSSMgr.cpp
Go to the documentation of this file.
1 /**
2  * @file VPSSMgr.cpp
3  * Definition file for a virtual base class that manages
4  * the calculation of standard state properties for all of the
5  * species in a single phase, assuming a variable P and T standard state
6  * (see \ref mgrpdssthermocalc and
7  * class \link Cantera::VPSSMgr VPSSMgr\endlink).
8  */
9 /*
10  * Copyright (2005) Sandia Corporation. Under the terms of
11  * Contract DE-AC04-94AL85000 with Sandia Corporation, the
12  * U.S. Government retains certain rights in this software.
13  */
14 
15 #include "cantera/thermo/VPSSMgr.h"
18 #include "cantera/thermo/PDSS.h"
20 
21 using namespace std;
22 
23 namespace Cantera
24 {
25 
26 class SpeciesThermo;
27 
28 VPSSMgr::VPSSMgr(VPStandardStateTP* vptp_ptr, SpeciesThermo* spthermo) :
29  m_kk(0),
30  m_vptp_ptr(vptp_ptr),
31  m_spthermo(spthermo),
32  m_tlast(-1.0),
33  m_plast(-1.0),
34  m_p0(-1.0),
35  m_minTemp(-1.0),
36  m_maxTemp(1.0E8),
37  m_useTmpRefStateStorage(false),
38  m_useTmpStandardStateStorage(false)
39 {
40  if (!m_vptp_ptr) {
41  throw CanteraError("VPSSMgr",
42  "null pointer for VPStandardStateTP is not permissible");
43  }
44 }
45 
47 {
48 }
49 
50 VPSSMgr::VPSSMgr(const VPSSMgr& right) :
51  m_kk(0),
52  m_vptp_ptr(0),
53  m_spthermo(0),
54  // m_Tnow(300.),
55  // m_Pnow(OneAtm),
56  m_tlast(-1.0),
57  m_plast(-1.0),
58  m_p0(-1.0),
59  m_minTemp(-1.0),
60  m_maxTemp(1.0E8),
61  m_useTmpRefStateStorage(false),
62  m_useTmpStandardStateStorage(false)
63 {
64  *this = right;
65 }
66 
67 //====================================================================================================================
68 /*
69  * Assigment operator
70  * We use a shallow copy strategy here. Note, this will have to be fixed up later.
71  */
72 VPSSMgr&
74 {
75  if (&right == this) {
76  return *this;
77  }
78  m_kk = right.m_kk;
79  /*
80  * What we are doing here is to make a shallow copy of the VPStandardStateTP
81  * pointer in the "new" VPSSMgr object using the value from the "old"
82  * VPSSMgr object. This is not appropriate if we are making a copy of a ThermoPhase
83  * object and the VPSSMgr objects are owned by the ThermoPhase object.
84  *
85  * The new object will want to have a different value of m_vptp_ptr than the
86  * value this is being copied here. It will want to refer to the copy of the
87  * VPStandardStateTP object being made that will own the new VPSSMgr object.
88  * However, the assignment object is not the place to carry out this fixup.
89  *
90  * We will have to "fix" up the shallow copies later.
91  */
92  m_vptp_ptr = right.m_vptp_ptr;
93  m_spthermo = right.m_spthermo;
94  m_tlast = -1.0;
95  m_plast = -1.0;
96  m_p0 = right.m_p0;
97  m_minTemp = right.m_minTemp;
98  m_maxTemp = right.m_maxTemp;
100  m_h0_RT = right.m_h0_RT;
101  m_cp0_R = right.m_cp0_R;
102  m_g0_RT = right.m_g0_RT;
103  m_s0_R = right.m_s0_R;
104  m_V0 = right.m_V0;
106  m_hss_RT = right.m_hss_RT;
107  m_cpss_R = right.m_cpss_R;
108  m_gss_RT = right.m_gss_RT;
109  m_sss_R = right.m_sss_R;
110  m_Vss = right.m_Vss;
111 
112  mPDSS_h0_RT = right.mPDSS_h0_RT;
113  mPDSS_cp0_R = right.mPDSS_cp0_R;
114  mPDSS_g0_RT = right.mPDSS_g0_RT;
115  mPDSS_s0_R = right.mPDSS_s0_R;
116  mPDSS_V0 = right.mPDSS_V0;
117  mPDSS_hss_RT = right.mPDSS_hss_RT;
118  mPDSS_cpss_R = right.mPDSS_cpss_R;
119  mPDSS_gss_RT = right.mPDSS_gss_RT;
120  mPDSS_sss_R = right.mPDSS_sss_R;
121  mPDSS_Vss = right.mPDSS_Vss;
122 
123  return *this;
124 }
125 //====================================================================================================================
127 {
128  VPSSMgr* vp = new VPSSMgr(*this);
129  return vp;
130 }
131 //====================================================================================================================
133  SpeciesThermo* sp_ptr)
134 {
135  m_vptp_ptr = vp_ptr;
136  m_spthermo = sp_ptr;
137 
138  // Take care of STITTbyPDSS objects
139 
140  // Go see if the SpeciesThermo type is a GeneralSpeciesThermo
141  GeneralSpeciesThermo* gst = dynamic_cast<GeneralSpeciesThermo*>(sp_ptr);
142  if (gst) {
143  for (size_t k = 0; k < m_kk; k++) {
144  SpeciesThermoInterpType* st = gst->provideSTIT(k);
145  STITbyPDSS* stpd = dynamic_cast<STITbyPDSS*>(st);
146  if (stpd) {
147  PDSS* PDSS_ptr = vp_ptr->providePDSS(k);
148  stpd->initAllPtrs(k, this, PDSS_ptr);
149  }
150  }
151  }
152 
153 }
154 //====================================================================================================================
155 // Standard States
156 
157 void
159 {
161  std::copy(m_gss_RT.begin(), m_gss_RT.end(), mu);
162  doublereal _rt = GasConstant * m_tlast;
163  scale(mu, mu+m_kk, mu, _rt);
164  } else {
165  err("getStandardChemPotentials");
166  }
167 }
168 
169 void
170 VPSSMgr::getGibbs_RT(doublereal* grt) const
171 {
173  std::copy(m_gss_RT.begin(), m_gss_RT.end(), grt);
174  } else {
175  err("getGibbs_RT");
176  }
177 }
178 
179 void
180 VPSSMgr::getEnthalpy_RT(doublereal* hrt) const
181 {
183  std::copy(m_hss_RT.begin(), m_hss_RT.end(), hrt);
184  } else {
185  err("getEnthalpy_RT");
186  }
187 }
188 
189 void
190 VPSSMgr::getEntropy_R(doublereal* sr) const
191 {
193  std::copy(m_sss_R.begin(), m_sss_R.end(), sr);
194  } else {
195  err("getEntropy_RT");
196  }
197 }
198 
199 void
200 VPSSMgr::getIntEnergy_RT(doublereal* urt) const
201 {
203  std::copy(m_hss_RT.begin(), m_hss_RT.end(), urt);
204  doublereal pRT = m_plast / (GasConstant * m_tlast);
205  for (size_t k = 0; k < m_kk; k++) {
206  urt[k] -= pRT * m_Vss[k];
207  }
208  } else {
209  err("getEntropy_RT");
210  }
211 }
212 
213 void
214 VPSSMgr::getCp_R(doublereal* cpr) const
215 {
217  std::copy(m_cpss_R.begin(), m_cpss_R.end(), cpr);
218  } else {
219  err("getCp_R");
220  }
221 }
222 
223 void
224 VPSSMgr::getStandardVolumes(doublereal* vol) const
225 {
227  std::copy(m_Vss.begin(), m_Vss.end(), vol);
228  } else {
229  err("getStandardVolumes");
230  }
231 }
232 
233 /*****************************************************************/
234 void
235 VPSSMgr::getEnthalpy_RT_ref(doublereal* hrt) const
236 {
238  std::copy(m_h0_RT.begin(), m_h0_RT.end(), hrt);
239  } else {
240  err("getEnthalpy_RT_ref");
241  }
242 }
243 
244 void
245 VPSSMgr::getGibbs_RT_ref(doublereal* grt) const
246 {
248  std::copy(m_g0_RT.begin(), m_g0_RT.end(), grt);
249  } else {
250  err("getGibbs_RT_ref");
251  }
252 }
253 
254 void
255 VPSSMgr::getGibbs_ref(doublereal* g) const
256 {
258  std::copy(m_g0_RT.begin(), m_g0_RT.end(), g);
259  doublereal _rt = GasConstant * m_tlast;
260  scale(g, g+m_kk, g, _rt);
261  } else {
262  err("getGibbs_ref");
263  }
264 }
265 
266 void
267 VPSSMgr::getEntropy_R_ref(doublereal* sr) const
268 {
270  std::copy(m_s0_R.begin(), m_s0_R.end(), sr);
271  } else {
272  err("getEntropy_R_ref");
273  }
274 }
275 
276 void
277 VPSSMgr::getCp_R_ref(doublereal* cpr) const
278 {
280  std::copy(m_cp0_R.begin(), m_cp0_R.end(), cpr);
281  } else {
282  err("getCp_R_ref");
283  }
284 }
285 
286 void
287 VPSSMgr::getStandardVolumes_ref(doublereal* vol) const
288 {
289  getStandardVolumes(vol);
290  //err("getStandardVolumes_ref");
291 }
292 
293 /*****************************************************************/
294 
295 void VPSSMgr::setState_P(doublereal pres)
296 {
297  if (m_plast != pres) {
298  m_plast = pres;
300  }
301 }
302 
303 void VPSSMgr::setState_T(doublereal temp)
304 {
305  if (m_tlast != temp) {
306  m_tlast = temp;
309  }
310 }
311 
312 void VPSSMgr::setState_TP(doublereal temp, doublereal pres)
313 {
314  if (m_tlast != temp) {
315  m_tlast = temp;
316  m_plast = pres;
319  } else if (m_plast != pres) {
320  m_plast = pres;
322  }
323 }
324 
326 {
328 }
329 
331 {
333 }
334 
336 {
337  for (size_t k = 0; k < m_kk; k++) {
338  PDSS* kPDSS = m_vptp_ptr->providePDSS(k);
339  kPDSS->setState_TP(m_tlast, m_plast);
340  }
341  err("_updateStandardStateThermo()");
342 }
343 
345 {
346  if (m_spthermo) {
347  m_spthermo->update(m_tlast, &m_cp0_R[0], &m_h0_RT[0], &m_s0_R[0]);
348  for (size_t k = 0; k < m_kk; k++) {
349  m_g0_RT[k] = m_h0_RT[k] - m_s0_R[k];
350  }
351  }
352 }
353 
354 
355 /*****************************************************************/
356 
357 void
359 {
360  initLengths();
361 }
362 
363 void
365 {
366  m_kk = m_vptp_ptr->nSpecies();
367  m_h0_RT.resize(m_kk, 0.0);
368  m_cp0_R.resize(m_kk, 0.0);
369  m_g0_RT.resize(m_kk, 0.0);
370  m_s0_R.resize(m_kk, 0.0);
371  m_V0.resize(m_kk, 0.0);
372  m_hss_RT.resize(m_kk, 0.0);
373  m_cpss_R.resize(m_kk, 0.0);
374  m_gss_RT.resize(m_kk, 0.0);
375  m_sss_R.resize(m_kk, 0.0);
376  m_Vss.resize(m_kk, 0.0);
377 
378 
379  // Storage used by the PDSS objects to store their
380  // answers.
381  mPDSS_h0_RT.resize(m_kk, 0.0);
382  mPDSS_cp0_R.resize(m_kk, 0.0);
383  mPDSS_g0_RT.resize(m_kk, 0.0);
384  mPDSS_s0_R.resize(m_kk, 0.0);
385  mPDSS_V0.resize(m_kk, 0.0);
386  mPDSS_hss_RT.resize(m_kk, 0.0);
387  mPDSS_cpss_R.resize(m_kk, 0.0);
388  mPDSS_gss_RT.resize(m_kk, 0.0);
389  mPDSS_sss_R.resize(m_kk, 0.0);
390  mPDSS_Vss.resize(m_kk, 0.0);
391 }
392 
393 void VPSSMgr::initThermoXML(XML_Node& phaseNode, std::string id)
394 {
395  const PDSS* kPDSS = m_vptp_ptr->providePDSS(0);
396  m_p0 = kPDSS->refPressure();
397  for (size_t i = 0; i < m_kk; i++) {
398  const PDSS* kPDSS = m_vptp_ptr->providePDSS(i);
399  doublereal mint = kPDSS->minTemp();
400  if (mint > m_minTemp) {
401  m_minTemp = mint;
402  }
403  mint = kPDSS->maxTemp();
404  if (mint < m_maxTemp) {
405  m_maxTemp = mint;
406  }
407  }
408 #ifdef DEBUG_MODE
409  // Add a check to see that all references pressures are the same
410  double m_p0_k;
411  if (m_spthermo) {
412  for (size_t k = 0; k < m_kk; k++) {
413  m_p0_k = m_spthermo->refPressure(k);
414  if (m_p0 != m_p0_k) {
415  //throw CanteraError("VPSSMgr::initThermoXML",
416  // "inconsistent ref pressures" + fp2str(m_p0) + " "
417  // + fp2str(m_p0_k));
418  // writelog("VPSSMgr::initThermoXML:"
419  // "inconsistent ref pressures: " + fp2str(m_p0) + " "
420  // + fp2str(m_p0_k) + " for SpeciesThermo k = " + int2str(k) + "\n");
421  }
422  }
423  }
424 
425  for (size_t k = 0; k < m_kk; k++) {
426  const PDSS* kPDSS = m_vptp_ptr->providePDSS(k);
427  m_p0_k = kPDSS->refPressure();
428  if (m_p0 != m_p0_k) {
429  //throw CanteraError("VPSSMgr::initThermoXML",
430  // "inconsistent ref pressures" + fp2str(m_p0) + " "
431  // + fp2str(m_p0_k));
432  //writelog("VPSSMgr::initThermoXML"
433  // "inconsistent ref pressures: " + fp2str(m_p0) + " "
434  // + fp2str(m_p0_k) + " for PDSS k = " + int2str(k) + "\n");
435  }
436  }
437 #endif
438 }
439 
440 void VPSSMgr::installSTSpecies(size_t k, const XML_Node& s,
441  const XML_Node* phaseNode_ptr)
442 {
443 
445  f->installThermoForSpecies(k, s, m_vptp_ptr, *m_spthermo, phaseNode_ptr);
446  if (m_p0 < 0.0) {
448  }
449 }
450 
452  const XML_Node* phaseNode_ptr)
453 {
454  err("VPSSMgr::createInstallPDSS");
455  return (PDSS*) 0;
456 }
457 
458 
459 /*****************************************************************/
460 doublereal VPSSMgr::minTemp(size_t k) const
461 {
462  if (k != npos) {
463  const PDSS* kPDSS = m_vptp_ptr->providePDSS(k);
464  return kPDSS->minTemp();
465  }
466  return m_minTemp;
467 }
468 
469 doublereal VPSSMgr::maxTemp(size_t k) const
470 {
471  if (k != npos) {
472  const PDSS* kPDSS = m_vptp_ptr->providePDSS(k);
473  return kPDSS->maxTemp();
474  }
475  return m_maxTemp;
476 }
477 
478 doublereal VPSSMgr::refPressure(size_t k) const
479 {
480  if (k != npos) {
481  const PDSS* kPDSS = m_vptp_ptr->providePDSS(k);
482  return kPDSS->refPressure();
483  }
484  return m_p0;
485 }
486 
488 {
489  err("reportPDSSType()");
490  return cPDSS_UNDEF;
491 }
492 
493 
495 {
496  err("reportVPSSType()");
497  return cVPSSMGR_UNDEF;
498 }
499 
500 /*****************************************************************/
501 
502 void VPSSMgr::err(std::string msg) const
503 {
504  throw CanteraError("VPSSMgr::" + msg, "unimplemented");
505 }
506 }
507 
508