[Python] Add basic access to Species objects
This commit is contained in:
parent
aee6cc14ac
commit
71f912d211
4 changed files with 109 additions and 2 deletions
|
|
@ -38,6 +38,21 @@ cdef extern from "cantera/cython/funcWrapper.h":
|
|||
CxxFunc1(callback_wrapper, void*)
|
||||
double eval(double) except +translate_exception
|
||||
|
||||
cdef extern from "cantera/base/smart_ptr.h":
|
||||
cppclass shared_ptr "Cantera::shared_ptr" [T]:
|
||||
T* get()
|
||||
void reset(T*)
|
||||
|
||||
cdef extern from "cantera/thermo/Species.h":
|
||||
cdef cppclass CxxSpecies "Cantera::Species":
|
||||
CxxSpecies()
|
||||
CxxSpecies(string, stdmap[string,double])
|
||||
|
||||
string name
|
||||
stdmap[string,double] composition
|
||||
double charge
|
||||
double size
|
||||
|
||||
|
||||
cdef extern from "cantera/thermo/ThermoPhase.h" namespace "Cantera":
|
||||
cdef cppclass CxxThermoPhase "Cantera::ThermoPhase":
|
||||
|
|
@ -75,6 +90,8 @@ cdef extern from "cantera/thermo/ThermoPhase.h" namespace "Cantera":
|
|||
|
||||
# species properties
|
||||
size_t nSpecies()
|
||||
shared_ptr[CxxSpecies] species(string) except +
|
||||
shared_ptr[CxxSpecies] species(size_t) except +
|
||||
size_t speciesIndex(string) except +
|
||||
string speciesName(size_t) except +
|
||||
double nAtoms(size_t, size_t) except +
|
||||
|
|
@ -588,6 +605,12 @@ ctypedef void (*transportMethod2d)(CxxTransport*, size_t, double*) except +
|
|||
ctypedef void (*kineticsMethod1d)(CxxKinetics*, double*) except +
|
||||
|
||||
# classes
|
||||
cdef class Species:
|
||||
cdef shared_ptr[CxxSpecies] _species
|
||||
cdef CxxSpecies* species
|
||||
|
||||
cdef _assign(self, shared_ptr[CxxSpecies] other)
|
||||
|
||||
cdef class _SolutionBase:
|
||||
cdef CxxThermoPhase* thermo
|
||||
cdef CxxKinetics* kinetics
|
||||
|
|
|
|||
|
|
@ -624,3 +624,36 @@ ideal_gas(name='spam', elements='O H',
|
|||
def test_checkReactionBalance(self):
|
||||
with self.assertRaises(Exception):
|
||||
ct.Solution('../data/h2o2_unbalancedReaction.xml')
|
||||
|
||||
|
||||
class TestSpecies(utilities.CanteraTest):
|
||||
def test_standalone(self):
|
||||
s = ct.Species('CH4', {'C':1, 'H':4})
|
||||
|
||||
self.assertEqual(s.name, 'CH4')
|
||||
c = s.composition
|
||||
self.assertEqual(len(c), 2)
|
||||
self.assertEqual(c['C'], 1)
|
||||
self.assertEqual(c['H'], 4)
|
||||
|
||||
def test_defaults(self):
|
||||
s = ct.Species('H2')
|
||||
self.assertEqual(s.size, 0.0)
|
||||
self.assertEqual(s.charge, 0.0)
|
||||
|
||||
def test_index_accessor(self):
|
||||
gas = ct.Solution('h2o2.xml')
|
||||
|
||||
for k in range(gas.n_species):
|
||||
s = gas.species(k)
|
||||
self.assertEqual(s.name, gas.species_name(k))
|
||||
|
||||
for m,n in s.composition.items():
|
||||
self.assertEqual(n, gas.n_atoms(k,m))
|
||||
|
||||
def test_name_accessor(self):
|
||||
gas = ct.Solution('h2o2.xml')
|
||||
|
||||
for name in gas.species_names:
|
||||
s = gas.species(name)
|
||||
self.assertEqual(s.name, name)
|
||||
|
|
|
|||
|
|
@ -13,6 +13,47 @@ cdef stdmap[string,double] comp_map(dict X) except *:
|
|||
m[stringify(species)] = value
|
||||
return m
|
||||
|
||||
cdef comp_map_to_dict(stdmap[string,double] m):
|
||||
return {pystr(species):value for species,value in m.items()}
|
||||
|
||||
|
||||
cdef class Species:
|
||||
def __cinit__(self, *args, init=True, **kwargs):
|
||||
if init:
|
||||
self._species.reset(new CxxSpecies())
|
||||
self.species = self._species.get()
|
||||
|
||||
def __init__(self, name=None, composition=None, charge=None, size=None,
|
||||
*args, init=True, **kwargs):
|
||||
if not init:
|
||||
return
|
||||
|
||||
if name is not None:
|
||||
self.species.name = stringify(name)
|
||||
|
||||
if composition is not None:
|
||||
self.species.composition = comp_map(composition)
|
||||
|
||||
cdef _assign(self, shared_ptr[CxxSpecies] other):
|
||||
self._species = other
|
||||
self.species = self._species.get()
|
||||
|
||||
property name:
|
||||
def __get__(self):
|
||||
return pystr(self.species.name)
|
||||
|
||||
property composition:
|
||||
def __get__(self):
|
||||
return comp_map_to_dict(self.species.composition)
|
||||
|
||||
property charge:
|
||||
def __get__(self):
|
||||
return self.species.charge
|
||||
|
||||
property size:
|
||||
def __get__(self):
|
||||
return self.species.size
|
||||
|
||||
|
||||
cdef class ThermoPhase(_SolutionBase):
|
||||
"""
|
||||
|
|
@ -237,6 +278,16 @@ cdef class ThermoPhase(_SolutionBase):
|
|||
|
||||
return index
|
||||
|
||||
def species(self, k):
|
||||
s = Species(init=False)
|
||||
if isinstance(k, (str, unicode)):
|
||||
s._assign(self.thermo.species(stringify(k)))
|
||||
elif isinstance(k, (int, float)):
|
||||
s._assign(self.thermo.species(<int>k))
|
||||
else:
|
||||
raise TypeError("Argument must be a string or a number")
|
||||
return s
|
||||
|
||||
def n_atoms(self, species, element):
|
||||
"""
|
||||
Number of atoms of element *element* in species *species*. The element
|
||||
|
|
|
|||
|
|
@ -9,8 +9,8 @@
|
|||
namespace Cantera {
|
||||
|
||||
Species::Species()
|
||||
: charge(std::numeric_limits<double>::quiet_NaN())
|
||||
, size(std::numeric_limits<double>::quiet_NaN())
|
||||
: charge(0.0)
|
||||
, size(0.0)
|
||||
{
|
||||
}
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue