Cantera  3.2.0a2
Loading...
Searching...
No Matches
PlasmaPhase.cpp
Go to the documentation of this file.
1//! @file PlasmaPhase.cpp
2
3// This file is part of Cantera. See License.txt in the top-level directory or
4// at https://cantera.org/license.txt for license and copyright information.
5
8#include <boost/math/special_functions/gamma.hpp>
10#include "cantera/base/global.h"
11#include "cantera/numerics/eigen_dense.h"
15#include <boost/polymorphic_pointer_cast.hpp>
17
18namespace Cantera {
19
20namespace {
21 const double gamma = sqrt(2 * ElectronCharge / ElectronMass);
22}
23
24PlasmaPhase::PlasmaPhase(const string& inputFile, const string& id_)
25{
26 initThermoFile(inputFile, id_);
27
28 // initial electron temperature
30
31 // Initialize the Boltzmann Solver
32 m_eedfSolver = make_unique<EEDFTwoTermApproximation>(this);
33
34 // Set Energy Grid (Hardcoded Defaults for Now)
35 double kTe_max = 60;
36 size_t nGridCells = 301;
37 m_nPoints = nGridCells + 1;
38 m_eedfSolver->setLinearGrid(kTe_max, nGridCells);
39 m_electronEnergyLevels = MappedVector(m_eedfSolver->getGridEdge().data(), m_nPoints);
40}
41
42PlasmaPhase::~PlasmaPhase()
43{
44 if (shared_ptr<Solution> soln = m_soln.lock()) {
45 soln->removeChangedCallback(this);
46 soln->kinetics()->removeReactionAddedCallback(this);
47 }
48 for (size_t k = 0; k < nCollisions(); k++) {
49 // remove callback
50 m_collisions[k]->removeSetRateCallback(this);
51 }
52}
53
55{
56 if (m_distributionType == "discretized") {
57 throw CanteraError("PlasmaPhase::updateElectronEnergyDistribution",
58 "Invalid for discretized electron energy distribution.");
59 } else if (m_distributionType == "isotropic") {
61 } else if (m_distributionType == "Boltzmann-two-term") {
62 auto ierr = m_eedfSolver->calculateDistributionFunction();
63 if (ierr == 0) {
64 auto y = m_eedfSolver->getEEDFEdge();
65 m_electronEnergyDist = Eigen::Map<const Eigen::ArrayXd>(y.data(), m_nPoints);
66 } else {
67 throw CanteraError("PlasmaPhase::updateElectronEnergyDistribution",
68 "Call to calculateDistributionFunction failed.");
69 }
70 bool validEEDF = (
72 m_electronEnergyDist.allFinite() &&
73 m_electronEnergyDist.maxCoeff() > 0.0 &&
74 m_electronEnergyDist.sum() > 0.0
75 );
76
77 if (validEEDF) {
79 } else {
80 writelog("Skipping Te update: EEDF is empty, non-finite, or unnormalized.\n");
81 }
82 } else {
83 throw CanteraError("PlasmaPhase::updateElectronEnergyDistribution",
84 "Unknown method '{}' for determining EEDF", m_distributionType);
85 }
88}
89
91 Eigen::ArrayXd eps32 = m_electronEnergyLevels.pow(3./2.);
92 double norm = 2./3. * numericalQuadrature(m_quadratureMethod,
94 if (norm < 0.0) {
95 throw CanteraError("PlasmaPhase::normalizeElectronEnergyDistribution",
96 "The norm is negative. This might be caused by bad "
97 "electron energy distribution");
98 }
100}
101
103{
104 if (type == "discretized" ||
105 type == "isotropic" ||
106 type == "Boltzmann-two-term") {
108 } else {
109 throw CanteraError("PlasmaPhase::setElectronEnergyDistributionType",
110 "Unknown type for electron energy distribution.");
111 }
112}
113
115{
117 double x = m_isotropicShapeFactor;
118 double gamma1 = boost::math::tgamma(3.0 / 2.0 / x);
119 double gamma2 = boost::math::tgamma(5.0 / 2.0 / x);
120 double c1 = x * std::pow(gamma2, 1.5) / std::pow(gamma1, 2.5);
121 double c2 = std::pow(gamma2 / gamma1, x);
123 c1 / std::pow(meanElectronEnergy(), 1.5) *
124 (-c2 * (m_electronEnergyLevels /
125 meanElectronEnergy()).pow(x)).exp();
127}
128
130 m_electronTemp = Te;
132}
133
135 m_electronTemp = 2.0 / 3.0 * energy * ElectronCharge / Boltzmann;
137}
138
139void PlasmaPhase::setElectronEnergyLevels(const double* levels, size_t length)
140{
141 m_nPoints = length;
142 m_electronEnergyLevels = Eigen::Map<const Eigen::ArrayXd>(levels, length);
146}
147
149{
150 m_distNum++;
151}
152
154{
155 m_levelNum++;
156 // Cross sections are interpolated on the energy levels
157 if (m_collisions.size() > 0) {
158 vector<double> energyLevels(m_nPoints);
159 MappedVector(energyLevels.data(), m_nPoints) = m_electronEnergyLevels;
160 for (shared_ptr<Reaction> collision : m_collisions) {
161 const auto& rate = boost::polymorphic_pointer_downcast
163 rate->updateInterpolatedCrossSection(energyLevels);
164 }
165 }
166}
167
169{
170 Eigen::ArrayXd h = m_electronEnergyLevels.tail(m_nPoints - 1) -
172 if (m_electronEnergyLevels[0] < 0.0 || (h <= 0.0).any()) {
173 throw CanteraError("PlasmaPhase::checkElectronEnergyLevels",
174 "Values of electron energy levels need to be positive and "
175 "monotonically increasing.");
176 }
177}
178
180{
181 Eigen::ArrayXd h = m_electronEnergyLevels.tail(m_nPoints - 1) -
183 if ((m_electronEnergyDist < 0.0).any()) {
184 throw CanteraError("PlasmaPhase::checkElectronEnergyDistribution",
185 "Values of electron energy distribution cannot be negative.");
186 }
187 if (m_electronEnergyDist[m_nPoints - 1] > 0.01) {
188 warn_user("PlasmaPhase::checkElectronEnergyDistribution",
189 "The value of the last element of electron energy distribution exceed 0.01. "
190 "This indicates that the value of electron energy level is not high enough "
191 "to contain the isotropic distribution at mean electron energy of "
192 "{} eV", meanElectronEnergy());
193 }
194}
195
197 const double* dist,
198 size_t length)
199{
200 m_distributionType = "discretized";
201 m_nPoints = length;
203 Eigen::Map<const Eigen::ArrayXd>(levels, length);
205 Eigen::Map<const Eigen::ArrayXd>(dist, length);
209 }
215}
216
218{
219 // calculate mean electron energy and electron temperature
220 Eigen::ArrayXd eps52 = m_electronEnergyLevels.pow(5./2.);
221 double epsilon_m = 2.0 / 5.0 * numericalQuadrature(m_quadratureMethod,
222 m_electronEnergyDist, eps52);
223 if (epsilon_m < 0.0 && m_quadratureMethod == "simpson") {
224 // try trapezoidal method
225 epsilon_m = 2.0 / 5.0 * numericalQuadrature(
226 "trapezoidal", m_electronEnergyDist, eps52);
227 }
228
229 if (epsilon_m < 0.0) {
230 throw CanteraError("PlasmaPhase::updateElectronTemperatureFromEnergyDist",
231 "The electron energy distribution produces negative electron temperature.");
232 }
233
234 m_electronTemp = 2.0 / 3.0 * epsilon_m * ElectronCharge / Boltzmann;
235}
236
238 m_isotropicShapeFactor = x;
240}
241
242void PlasmaPhase::getParameters(AnyMap& phaseNode) const
243{
245 AnyMap eedf;
246 eedf["type"] = m_distributionType;
247 vector<double> levels(m_nPoints);
248 Eigen::Map<Eigen::ArrayXd>(levels.data(), m_nPoints) = m_electronEnergyLevels;
249 eedf["energy-levels"] = levels;
250 if (m_distributionType == "isotropic") {
251 eedf["shape-factor"] = m_isotropicShapeFactor;
252 eedf["mean-electron-energy"].setQuantity(meanElectronEnergy(), "eV");
253 } else if (m_distributionType == "discretized") {
254 vector<double> dist(m_nPoints);
255 Eigen::Map<Eigen::ArrayXd>(dist.data(), m_nPoints) = m_electronEnergyDist;
256 eedf["distribution"] = dist;
257 eedf["normalize"] = m_do_normalizeElectronEnergyDist;
258 }
259 phaseNode["electron-energy-distribution"] = std::move(eedf);
260}
261
262void PlasmaPhase::setParameters(const AnyMap& phaseNode, const AnyMap& rootNode)
263{
264 IdealGasPhase::setParameters(phaseNode, rootNode);
265 if (phaseNode.hasKey("electron-energy-distribution")) {
266 const AnyMap eedf = phaseNode["electron-energy-distribution"].as<AnyMap>();
267 m_distributionType = eedf["type"].asString();
268 if (m_distributionType == "isotropic") {
269 if (eedf.hasKey("shape-factor")) {
270 setIsotropicShapeFactor(eedf["shape-factor"].asDouble());
271 } else {
272 throw CanteraError("PlasmaPhase::setParameters",
273 "isotropic type requires shape-factor key.");
274 }
275 if (eedf.hasKey("mean-electron-energy")) {
276 double energy = eedf.convert("mean-electron-energy", "eV");
277 setMeanElectronEnergy(energy);
278 } else {
279 throw CanteraError("PlasmaPhase::setParameters",
280 "isotropic type requires electron-temperature key.");
281 }
282 if (eedf.hasKey("energy-levels")) {
283 auto levels = eedf["energy-levels"].asVector<double>();
284 setElectronEnergyLevels(levels.data(), levels.size());
285 }
287 } else if (m_distributionType == "discretized") {
288 if (!eedf.hasKey("energy-levels")) {
289 throw CanteraError("PlasmaPhase::setParameters",
290 "Cannot find key energy-levels.");
291 }
292 if (!eedf.hasKey("distribution")) {
293 throw CanteraError("PlasmaPhase::setParameters",
294 "Cannot find key distribution.");
295 }
296 if (eedf.hasKey("normalize")) {
297 enableNormalizeElectronEnergyDist(eedf["normalize"].asBool());
298 }
299 auto levels = eedf["energy-levels"].asVector<double>();
300 auto distribution = eedf["distribution"].asVector<double>(levels.size());
301 setDiscretizedElectronEnergyDist(levels.data(), distribution.data(),
302 levels.size());
303 }
304 }
305
306 if (rootNode.hasKey("electron-collisions")) {
307 for (const auto& item : rootNode["electron-collisions"].asVector<AnyMap>()) {
308 auto rate = make_shared<ElectronCollisionPlasmaRate>(item);
309 Composition reactants, products;
310 reactants[item["target"].asString()] = 1;
311 reactants[electronSpeciesName()] = 1;
312 if (item.hasKey("product")) {
313 products[item["product"].asString()] = 1;
314 } else {
315 products[item["target"].asString()] = 1;
316 }
317 products[electronSpeciesName()] = 1;
318 if (rate->kind() == "ionization") {
319 products[electronSpeciesName()] += 1;
320 } else if (rate->kind() == "attachment") {
321 products[electronSpeciesName()] -= 1;
322 }
323 auto R = make_shared<Reaction>(reactants, products, rate);
324 addCollision(R);
325 }
326 }
327}
328
329bool PlasmaPhase::addSpecies(shared_ptr<Species> spec)
330{
331 bool added = IdealGasPhase::addSpecies(spec);
332 size_t k = m_kk - 1;
333
334 if ((spec->name == "e" || spec->name == "Electron") ||
335 (spec->composition.find("E") != spec->composition.end() &&
336 spec->composition.size() == 1 &&
337 spec->composition["E"] == 1)) {
340 } else {
341 throw CanteraError("PlasmaPhase::addSpecies",
342 "Cannot add species, {}. "
343 "Only one electron species is allowed.", spec->name);
344 }
345 }
346 return added;
347}
348
350{
352
353 // Check electron species
355 throw CanteraError("PlasmaPhase::initThermo",
356 "No electron species found.");
357 }
358}
359
360void PlasmaPhase::setSolution(std::weak_ptr<Solution> soln) {
362 // register callback function to be executed
363 // when the thermo or kinetics object changed
364 if (shared_ptr<Solution> soln = m_soln.lock()) {
365 soln->registerChangedCallback(this, [&]() {
367 });
368 }
369}
370
372{
373 if (shared_ptr<Solution> soln = m_soln.lock()) {
374 shared_ptr<Kinetics> kin = soln->kinetics();
375 if (!kin) {
376 return;
377 }
378
379 // add collision from the initial list of reactions. Only add reactions we
380 // haven't seen before
381 set<Reaction*> existing;
382 for (auto& R : m_collisions) {
383 existing.insert(R.get());
384 }
385 for (size_t i = 0; i < kin->nReactions(); i++) {
386 shared_ptr<Reaction> R = kin->reaction(i);
387 if (R->rate()->type() != "electron-collision-plasma"
388 || existing.count(R.get())) {
389 continue;
390 }
391 addCollision(R);
392 }
393
394 // register callback when reaction is added later
395 // Modifying collision reactions is not supported
396 kin->registerReactionAddedCallback(this, [this, kin]() {
397 size_t i = kin->nReactions() - 1;
398 if (kin->reaction(i)->type() == "electron-collision-plasma") {
399 addCollision(kin->reaction(i));
400 }
401 });
402 }
403}
404
405void PlasmaPhase::addCollision(shared_ptr<Reaction> collision)
406{
407 size_t i = nCollisions();
408
409 // setup callback to signal updating the cross-section-related
410 // parameters
411 collision->registerSetRateCallback(this, [this, i, collision]() {
412 m_interp_cs_ready[i] = false;
414 std::dynamic_pointer_cast<ElectronCollisionPlasmaRate>(collision->rate());
415 });
416
417 // Identify target species for electron-collision reactions
418 string target;
419 for (const auto& [name, _] : collision->reactants) {
420 // Reactants are expected to be electrons and the target species
421 if (name != electronSpeciesName()) {
423 target = name;
424 break;
425 }
426 }
427 if (target.empty()) {
428 throw CanteraError("PlasmaPhase::addCollision", "Error identifying target for"
429 " collision with equation '{}'", collision->equation());
430 }
431
432 m_collisions.emplace_back(collision);
433 m_collisionRates.emplace_back(
434 std::dynamic_pointer_cast<ElectronCollisionPlasmaRate>(collision->rate()));
435 m_interp_cs_ready.emplace_back(false);
436
437 // resize parameters
440
441 // Set up data used by Boltzmann solver
442 auto& rate = *m_collisionRates.back();
443 string kind = m_collisionRates.back()->kind();
444
445 if ((kind == "effective" || kind == "elastic")) {
446 for (size_t k = 0; k < m_collisions.size() - 1; k++) {
447 if (m_collisions[k]->reactants == collision->reactants &&
448 (m_collisionRates[k]->kind() == "elastic" ||
449 m_collisionRates[k]->kind() == "effective") && !collision->duplicate)
450 {
451 throw CanteraError("PlasmaPhase::addCollision", "Phase already contains"
452 " an effective/elastic cross section for '{}'.", target);
453 }
454 }
455 m_kElastic.push_back(i);
456 } else {
457 m_kInelastic.push_back(i);
458 }
459
460 m_energyLevels.push_back(rate.energyLevels());
461 m_crossSections.push_back(rate.crossSections());
462 m_eedfSolver->setGridCache();
463}
464
466{
467 if (m_interp_cs_ready[i]) {
468 return false;
469 }
470 vector<double> levels(m_nPoints);
471 Eigen::Map<Eigen::ArrayXd>(levels.data(), m_nPoints) = m_electronEnergyLevels;
472 m_collisionRates[i]->updateInterpolatedCrossSection(levels);
473 m_interp_cs_ready[i] = true;
474 return true;
475}
476
478{
480 // Forward difference for the first point
484
485 // Central difference for the middle points
486 for (size_t i = 1; i < m_nPoints - 1; i++) {
490 (h1 * h1 - h0 * h0) * m_electronEnergyDist[i] -
491 h1 * h1 * m_electronEnergyDist[i-1]) /
492 (h1 * h0) / (h1 + h0);
493 }
494
495 // Backward difference for the last point
501}
502
504{
505 // cache of cross section plus distribution plus energy-level number
506 static const int cacheId = m_cache.getId();
507 CachedScalar last_stateNum = m_cache.getScalar(cacheId);
508
509 // combine the distribution and energy level number
510 int stateNum = m_distNum + m_levelNum;
511
512 vector<bool> interpChanged(m_collisions.size());
513 for (size_t i = 0; i < m_collisions.size(); i++) {
514 interpChanged[i] = updateInterpolatedCrossSection(i);
515 }
516
517 if (last_stateNum.validate(temperature(), stateNum)) {
518 // check each cross section, and only update coefficients that
519 // the interpolated cross sections change
520 for (size_t i = 0; i < m_collisions.size(); i++) {
521 if (interpChanged[i]) {
523 }
524 }
525 } else {
526 // update every coefficient if distribution, temperature,
527 // or energy levels change.
528 for (size_t i = 0; i < m_collisions.size(); i++) {
530 }
531 }
532}
533
535{
536 // @todo exclude attachment collisions
537 size_t k = m_targetSpeciesIndices[i];
538
539 // Map cross sections to Eigen::ArrayXd
540 auto cs_array = Eigen::Map<const Eigen::ArrayXd>(
541 m_collisionRates[i]->crossSectionInterpolated().data(),
542 m_collisionRates[i]->crossSectionInterpolated().size()
543 );
544
545 // Mass ratio calculation
546 double mass_ratio = ElectronMass / molecularWeight(k) * Avogadro;
547
548 // Calculate the rate using Simpson's rule or trapezoidal rule
549 Eigen::ArrayXd f0_plus = m_electronEnergyDist + Boltzmann * temperature() /
551 m_elasticElectronEnergyLossCoefficients[i] = 2.0 * mass_ratio * gamma *
553 m_quadratureMethod, 1.0 / 3.0 * f0_plus.cwiseProduct(cs_array),
554 m_electronEnergyLevels.pow(3.0));
555}
556
558{
560 // The elastic power loss includes the contributions from inelastic
561 // collisions (inelastic recoil effects).
562 double rate = 0.0;
563 for (size_t i = 0; i < nCollisions(); i++) {
566 }
567
568 return Avogadro * Avogadro * ElectronCharge *
570}
571
573{
575 static const int cacheId = m_cache.getId();
576 CachedScalar cached = m_cache.getScalar(cacheId);
577 double tempNow = temperature();
578 double electronTempNow = electronTemperature();
579 size_t k = m_electronSpeciesIndex;
580 // If the electron temperature has changed since the last time these
581 // properties were computed, recompute them.
582 if (cached.state1 != tempNow || cached.state2 != electronTempNow) {
584 &m_cp0_R[k], &m_h0_RT[k], &m_s0_R[k]);
585 cached.state1 = tempNow;
586 cached.state2 = electronTempNow;
587 }
588 // update the species Gibbs functions
589 m_g0_RT[k] = m_h0_RT[k] - m_s0_R[k];
590}
591
593 double value = IdealGasPhase::enthalpy_mole();
594 value += GasConstant * (electronTemperature() - temperature()) *
597 return value;
598}
599
600void PlasmaPhase::getGibbs_ref(double* g) const
601{
604}
605
607{
610}
611
613{
616}
617
619{
621 double logp = log(pressure());
622 double logpe = log(electronPressure());
623 sbar[m_electronSpeciesIndex] += GasConstant * (logp - logpe);
624}
625
627{
628 const vector<double>& _h = enthalpy_RT_ref();
629 for (size_t k = 0; k < m_kk; k++) {
630 ubar[k] = RT() * (_h[k] - 1.0);
631 }
632 size_t k = m_electronSpeciesIndex;
633 ubar[k] = RTe() * (_h[k] - 1.0);
634}
635
636void PlasmaPhase::getChemPotentials(double* mu) const
637{
639 size_t k = m_electronSpeciesIndex;
640 double xx = std::max(SmallNumber, moleFraction(k));
641 mu[k] += (RTe() - RT()) * log(xx);
642}
643
645{
647 size_t k = m_electronSpeciesIndex;
648 muStar[k] -= log(pressure() / refPressure()) * RT();
649 muStar[k] += log(electronPressure() / refPressure()) * RTe();
650}
651
652void PlasmaPhase::getEntropy_R(double* sr) const
653{
654 const vector<double>& _s = entropy_R_ref();
655 copy(_s.begin(), _s.end(), sr);
656 double tmp = log(pressure() / refPressure());
657 for (size_t k = 0; k < m_kk; k++) {
658 if (k != m_electronSpeciesIndex) {
659 sr[k] -= tmp;
660 } else {
661 sr[k] -= log(electronPressure() / refPressure());
662 }
663 }
664}
665
666void PlasmaPhase::getGibbs_RT(double* grt) const
667{
668 const vector<double>& gibbsrt = gibbs_RT_ref();
669 copy(gibbsrt.begin(), gibbsrt.end(), grt);
670 double tmp = log(pressure() / refPressure());
671 for (size_t k = 0; k < m_kk; k++) {
672 if (k != m_electronSpeciesIndex) {
673 grt[k] += tmp;
674 } else {
675 grt[k] += log(electronPressure() / refPressure());
676 }
677 }
678}
679
680}
EEDF Two-Term approximation solver.
Header for plasma reaction rates parameterized by electron collision cross section and electron energ...
Base class for kinetics managers and also contains the kineticsmgr module documentation (see Kinetics...
Header file for class PlasmaPhase.
Declaration for class Cantera::Species.
A map of string keys to values whose type can vary at runtime.
Definition AnyMap.h:431
bool hasKey(const string &key) const
Returns true if the map contains an item named key.
Definition AnyMap.cpp:1477
double convert(const string &key, const string &units) const
Convert the item stored by the given key to the units specified in units.
Definition AnyMap.cpp:1595
Base class for exceptions thrown by Cantera classes.
Electron collision plasma reaction rate type.
void updateInterpolatedCrossSection(const vector< double > &)
Update the value of m_crossSectionsInterpolated [m2].
const vector< double > & entropy_R_ref() const
Returns a reference to the dimensionless reference state Entropy vector.
double enthalpy_mole() const override
Return the Molar enthalpy. Units: J/kmol.
void getPartialMolarEnthalpies(double *hbar) const override
Returns an array of partial molar enthalpies for the species in the mixture.
void getChemPotentials(double *mu) const override
Get the species chemical potentials. Units: J/kmol.
double pressure() const override
Pressure.
vector< double > m_g0_RT
Temporary storage for dimensionless reference state Gibbs energies.
vector< double > m_h0_RT
Temporary storage for dimensionless reference state enthalpies.
void getGibbs_ref(double *g) const override
Returns the vector of the Gibbs function of the reference state at the current temperature of the sol...
void getStandardChemPotentials(double *mu) const override
Get the array of chemical potentials at unit activity for the species at their standard states at the...
const vector< double > & gibbs_RT_ref() const
Returns a reference to the dimensionless reference state Gibbs free energy vector.
void getStandardVolumes_ref(double *vol) const override
Get the molar volumes of the species reference states at the current T and P_ref of the solution.
virtual void updateThermo() const
Update the species reference state thermodynamic functions.
vector< double > m_s0_R
Temporary storage for dimensionless reference state entropies.
vector< double > m_cp0_R
Temporary storage for dimensionless reference state heat capacities.
bool addSpecies(shared_ptr< Species > spec) override
Add a Species to this Phase.
void getPartialMolarEntropies(double *sbar) const override
Returns an array of partial molar entropies of the species in the solution.
const vector< double > & enthalpy_RT_ref() const
Returns a reference to the dimensionless reference state enthalpy vector.
virtual void update_single(size_t k, double T, double *cp_R, double *h_RT, double *s_R) const
Get reference-state properties for a single species.
ValueCache m_cache
Cached for saved calculations within each ThermoPhase.
Definition Phase.h:835
size_t m_kk
Number of species in the phase.
Definition Phase.h:855
double temperature() const
Temperature (K).
Definition Phase.h:563
virtual double concentration(const size_t k) const
Concentration of species k.
Definition Phase.cpp:476
size_t speciesIndex(const string &name) const
Returns the index of a species named 'name' within the Phase object.
Definition Phase.cpp:129
double moleFraction(size_t k) const
Return the mole fraction of a single species.
Definition Phase.cpp:439
double molecularWeight(size_t k) const
Molecular weight of species k.
Definition Phase.cpp:383
string name() const
Return the name of the phase.
Definition Phase.cpp:20
void checkElectronEnergyDistribution() const
Check the electron energy distribution.
vector< vector< double > > m_energyLevels
Electron energy levels corresponding to the cross section data.
void setCollisions()
Set collisions.
double meanElectronEnergy() const
Mean electron energy [eV].
double enthalpy_mole() const override
Return the Molar enthalpy. Units: J/kmol.
size_t m_nPoints
Number of points of electron energy levels.
void addCollision(shared_ptr< Reaction > collision)
Add a collision and record the target species.
virtual void setSolution(std::weak_ptr< Solution > soln) override
Set the link to the Solution object that owns this ThermoPhase.
void getPartialMolarEnthalpies(double *hbar) const override
Returns an array of partial molar enthalpies for the species in the mixture.
void getChemPotentials(double *mu) const override
Get the species chemical potentials. Units: J/kmol.
void normalizeElectronEnergyDistribution()
Electron energy distribution norm.
void getStandardChemPotentials(double *muStar) const override
Get the array of chemical potentials at unit activity for the species at their standard states at the...
void updateThermo() const override
Update the species reference state thermodynamic functions.
vector< size_t > m_targetSpeciesIndices
The collision-target species indices of m_collisions.
void setElectronTemperature(double Te) override
Set the internally stored electron temperature of the phase (K).
void electronEnergyLevelChanged()
When electron energy level changed, plasma properties such as electron-collision reaction rates need ...
double elasticPowerLoss()
The elastic power loss (J/s/m³)
int m_levelNum
Electron energy level change variable.
bool updateInterpolatedCrossSection(size_t k)
Update interpolated cross section of a collision.
void electronEnergyDistributionChanged()
When electron energy distribution changed, plasma properties such as electron-collision reaction rate...
void getEntropy_R(double *sr) const override
Get the array of nondimensional Entropy functions for the standard state species at the current T and...
size_t nElectronEnergyLevels() const
Number of electron levels.
void getGibbs_ref(double *g) const override
Returns the vector of the Gibbs function of the reference state at the current temperature of the sol...
size_t nCollisions() const
Number of electron collision cross sections.
Eigen::ArrayXd m_electronEnergyDist
Normalized electron energy distribution vector [-] Length: m_nPoints.
Eigen::ArrayXd m_electronEnergyLevels
electron energy levels [ev]. Length: m_nPoints
void setDiscretizedElectronEnergyDist(const double *levels, const double *distrb, size_t length)
Set discretized electron energy distribution.
void getParameters(AnyMap &phaseNode) const override
Store the parameters of a ThermoPhase object such that an identical one could be reconstructed using ...
string type() const override
String indicating the thermodynamic model implemented.
void checkElectronEnergyLevels() const
Check the electron energy levels.
void initThermo() override
Initialize the ThermoPhase object after all species have been set up.
void updateElasticElectronEnergyLossCoefficients()
Update elastic electron energy loss coefficients.
void updateElectronTemperatureFromEnergyDist()
Update electron temperature (K) From energy distribution.
string m_distributionType
Electron energy distribution type.
void getStandardVolumes_ref(double *vol) const override
Get the molar volumes of the species reference states at the current T and P_ref of the solution.
void updateElectronEnergyDistribution()
Update the electron energy distribution.
vector< double > m_elasticElectronEnergyLossCoefficients
Elastic electron energy loss coefficients (eV m3/s)
string m_quadratureMethod
Numerical quadrature method for electron energy distribution.
PlasmaPhase(const string &inputFile="", const string &id="")
Construct and initialize a PlasmaPhase object directly from an input file.
double m_electronTemp
Electron temperature [K].
double RTe() const
Return the Gas Constant multiplied by the current electron temperature.
void setElectronEnergyLevels(const double *levels, size_t length)
Set electron energy levels.
void getGibbs_RT(double *grt) const override
Get the nondimensional Gibbs functions for the species in their standard states at the current T and ...
bool m_do_normalizeElectronEnergyDist
Flag of normalizing electron energy distribution.
void updateElectronEnergyDistDifference()
Update electron energy distribution difference.
void updateElasticElectronEnergyLossCoefficient(size_t i)
Updates the elastic electron energy loss coefficient for collision index i.
vector< size_t > m_kElastic
Indices of elastic collisions in m_crossSections.
unique_ptr< EEDFTwoTermApproximation > m_eedfSolver
Solver used to calculate the EEDF based on electron collision rates.
void getPartialMolarIntEnergies(double *ubar) const override
Return an array of partial molar internal energies for the species in the mixture.
string electronSpeciesName() const
Electron species name.
void setIsotropicElectronEnergyDistribution()
Set isotropic electron energy distribution.
Eigen::ArrayXd m_electronEnergyDistDiff
ionization degree for the electron-electron collisions (tmp is the previous one)
bool addSpecies(shared_ptr< Species > spec) override
Add a Species to this Phase.
const shared_ptr< Reaction > collision(size_t i) const
Get the Reaction object associated with electron collision i.
vector< bool > m_interp_cs_ready
The list of whether the interpolated cross sections is ready.
vector< shared_ptr< ElectronCollisionPlasmaRate > > m_collisionRates
The list of shared pointers of collision rates.
vector< shared_ptr< Reaction > > m_collisions
The list of shared pointers of plasma collision reactions.
void setParameters(const AnyMap &phaseNode, const AnyMap &rootNode=AnyMap()) override
Set equation of state parameters from an AnyMap phase description.
void setMeanElectronEnergy(double energy)
Set mean electron energy [eV].
size_t m_electronSpeciesIndex
Index of electron species.
vector< vector< double > > m_crossSections
Cross section data.
void setElectronEnergyDistributionType(const string &type)
Set electron energy distribution type.
void getPartialMolarEntropies(double *sbar) const override
Returns an array of partial molar entropies of the species in the solution.
virtual double electronPressure() const
Electron pressure.
vector< size_t > m_kInelastic
Indices of inelastic collisions in m_crossSections.
double electronTemperature() const override
Electron Temperature (K)
void setIsotropicShapeFactor(double x)
Set the shape factor of isotropic electron energy distribution.
void enableNormalizeElectronEnergyDist(bool enable)
Set flag of automatically normalize electron energy distribution Flag: m_do_normalizeElectronEnergyDi...
int m_distNum
Electron energy distribution change variable.
virtual void setParameters(const AnyMap &phaseNode, const AnyMap &rootNode=AnyMap())
Set equation of state parameters from an AnyMap phase description.
virtual void getParameters(AnyMap &phaseNode) const
Store the parameters of a ThermoPhase object such that an identical one could be reconstructed using ...
double RT() const
Return the Gas Constant multiplied by the current temperature.
virtual void setSolution(std::weak_ptr< Solution > soln)
Set the link to the Solution object that owns this ThermoPhase.
virtual void initThermo()
Initialize the ThermoPhase object after all species have been set up.
void initThermoFile(const string &inputFile, const string &id)
Initialize a ThermoPhase object using an input file.
std::weak_ptr< Solution > m_soln
reference to Solution
MultiSpeciesThermo m_spthermo
Pointer to the calculation manager for species reference-state thermodynamic properties.
virtual double refPressure() const
Returns the reference pressure in Pa.
CachedScalar getScalar(int id)
Get a reference to a CachedValue object representing a scalar (double) with the given id.
Definition ValueCache.h:161
int getId()
Get a unique id for a cached value.
Header for a file containing miscellaneous numerical functions.
This file contains definitions for utility functions and text for modules, inputfiles and logging,...
void writelog(const string &fmt, const Args &... args)
Write a formatted message to the screen.
Definition global.h:171
double numericalQuadrature(const string &method, const Eigen::ArrayXd &f, const Eigen::ArrayXd &x)
Numerical integration of a function.
Definition funcs.cpp:116
const double Boltzmann
Boltzmann constant [J/K].
Definition ct_defs.h:84
const double Avogadro
Avogadro's Number [number/kmol].
Definition ct_defs.h:81
const double GasConstant
Universal Gas Constant [J/kmol/K].
Definition ct_defs.h:120
const double ElectronCharge
Elementary charge [C].
Definition ct_defs.h:90
const double ElectronMass
Electron Mass [kg].
Definition ct_defs.h:111
void warn_user(const string &method, const string &msg, const Args &... args)
Print a user warning raised from method as CanteraWarning.
Definition global.h:263
Namespace for the Cantera kernel.
Definition AnyMap.cpp:595
const size_t npos
index returned by functions to indicate "no position"
Definition ct_defs.h:180
const double SmallNumber
smallest number to compare to zero.
Definition ct_defs.h:158
map< string, double > Composition
Map from string names to doubles.
Definition ct_defs.h:177
A cached property value and the state at which it was evaluated.
Definition ValueCache.h:33
double state2
Value of the second state variable for the state at which value was evaluated, for example density or...
Definition ValueCache.h:106
bool validate(double state1New)
Check whether the currently cached value is valid based on a single state variable.
Definition ValueCache.h:39
double state1
Value of the first state variable for the state at which value was evaluated, for example temperature...
Definition ValueCache.h:102