I - An example to start with ...

This first tutorial's main objective is to help you get started with the Python interface of Cantera. The goal here is to get acquainted with the notion of objects and functions that we will encounter in all Python scripts.
We will start by defining a simple gaseous object directly in a script, before introducing the Python terminal and its possibilities. Next, we will see how to access and modify the state of this newly instantiated gas object through adequate functions; before concluding with a general discussion on the specificities of gaseous objects.
The second objective of this first tutorial is to introduce the data file format of Cantera, which will be the subject of the second tutorial.

1. Importation of cantera

In [1]:
import cantera as ct
from cantera import ck2cti

2. Create solution from cti file

This will create an instance of the class Solution from cantera package.
The file gri30.xml contains all the important informations about the chemistry, meaning :
  • the properties of the different species
  • the reactions
  • the kinetics used
  • the type of transport used
In [2]:
gas = ct.Solution("gri30.xml")
NB : This could have also been written : gas = ct.Solution("gri30.cti").
Indeed, cti and xml are only two different format and can be read the same way by cantera. The only difference is that cti file are more human readable than xml files. If you want to put your cti into xml format, you can do the ctml_writer command as follows in the console :
ctml_writer blabla.cti You will see some more information about the structure and the data present in this file at the end of this tutorial.

3. Choose and print the thermodynamic state of the gas

To define the mixture of the gas correctly, it is necessary to define two thermodynamic parameters and the quantities of the different species ( molar fraction X or mass fraction Y ). These commands gives all the interesting informations for the gas state, namely the temperature, the pressure and the density of the mixture. It also gives information about the species in the mixture as mass fractions Y or molar fractions X.

NB : If you are lost, you can still use the function help to see what are the functions available for a gaseous object.

In [3]:
help(gas)
Help on Solution in module cantera.composite object:

class Solution(cantera._cantera.ThermoPhase, cantera._cantera.Kinetics, cantera._cantera.Transport)
 |  A class for chemically-reacting solutions. Instances can be created to
 |  represent any type of solution -- a mixture of gases, a liquid solution, or
 |  a solid solution, for example.
 |  
 |  Class `Solution` derives from classes `ThermoPhase`, `Kinetics`, and
 |  `Transport`.  It defines no methods of its own, and is provided so that a
 |  single object can be used to compute thermodynamic, kinetic, and transport
 |  properties of a solution.
 |  
 |  To skip initialization of the Transport object, pass the keyword argument
 |  ``transport_model=None`` to the `Solution` constructor.
 |  
 |  The most common way to instantiate `Solution` objects is by using a phase
 |  definition, species and reactions defined in an input file::
 |  
 |      gas = ct.Solution('gri30.cti')
 |  
 |  If an input file defines multiple phases, the phase *name* (in CTI) or *id*
 |  (in XML) can be used to specify the desired phase::
 |  
 |      gas = ct.Solution('diamond.cti', 'gas')
 |      diamond = ct.Solution('diamond.cti', 'diamond')
 |  
 |  `Solution` objects can also be constructed using `Species` and `Reaction`
 |  objects which can themselves either be imported from input files or defined
 |  directly in Python::
 |  
 |      spec = ct.Species.listFromFile('gri30.cti')
 |      rxns = ct.Reaction.listFromFile('gri30.cti')
 |      gas = ct.Solution(thermo='IdealGas', kinetics='GasKinetics',
 |                        species=spec, reactions=rxns)
 |  
 |  where the ``thermo`` and ``kinetics`` keyword arguments are strings
 |  specifying the thermodynamic and kinetics model, respectively, and
 |  ``species`` and ``reactions`` keyword arguments are lists of `Species` and
 |  `Reaction` objects, respectively.
 |  
 |  For non-trivial uses cases of this functionality, see the examples
 |  :ref:`py-example-extract_submechanism.py` and
 |  :ref:`py-example-mechanism_reduction.py`.
 |  
 |  In addition, `Solution` objects can be constructed by passing the text of
 |  the CTI or XML phase definition in directly, using the ``source`` keyword
 |  argument::
 |  
 |      cti_def = '''
 |          ideal_gas(name='gas', elements='O H Ar',
 |                    species='gri30: all',
 |                    reactions='gri30: all',
 |                    options=['skip_undeclared_elements', 'skip_undeclared_species', 'skip_undeclared_third_bodies'],
 |                    initial_state=state(temperature=300, pressure=101325))'''
 |      gas = ct.Solution(source=cti_def)
 |  
 |  Method resolution order:
 |      Solution
 |      cantera._cantera.ThermoPhase
 |      cantera._cantera.Kinetics
 |      cantera._cantera.Transport
 |      cantera._cantera._SolutionBase
 |      builtins.object
 |  
 |  Methods inherited from cantera._cantera.ThermoPhase:
 |  
 |  __call__(self, /, *args, **kwargs)
 |      Call self as a function.
 |  
 |  __init__(self, /, *args, **kwargs)
 |      Initialize self.  See help(type(self)) for accurate signature.
 |  
 |  add_species(...)
 |      ThermoPhase.add_species(self, Species species)
 |      
 |      Add a new species to this phase. Missing elements will be added
 |      automatically.
 |  
 |  atomic_weight(...)
 |      ThermoPhase.atomic_weight(self, m)
 |      Atomic weight [kg/kmol] of element *m*
 |  
 |  element_index(...)
 |      ThermoPhase.element_index(self, element) -> int
 |      
 |      The index of element *element*, which may be specified as a string or
 |      an integer. In the latter case, the index is checked for validity and
 |      returned. If no such element is present, an exception is thrown.
 |  
 |  element_name(...)
 |      ThermoPhase.element_name(self, m)
 |      Name of the element with index *m*.
 |  
 |  element_potentials(...)
 |      ThermoPhase.element_potentials(self)
 |      
 |      Get the array of element potentials. The element potentials are only
 |      defined for equilibrium states. This method first sets the composition
 |      to a state of equilibrium at constant T and P, then computes the
 |      element potentials for this equilibrium state.
 |  
 |  elemental_mass_fraction(...)
 |      ThermoPhase.elemental_mass_fraction(self, m)
 |      
 |      Get the elemental mass fraction :math:`Z_{\mathrm{mass},m}` of element
 |      :math:`m` as defined by:
 |      
 |      .. math:: Z_{\mathrm{mass},m} = \sum_k \frac{a_{m,k} M_m}{M_k} Y_k
 |      
 |      with :math:`a_{m,k}` being the number of atoms of element :math:`m` in
 |      species :math:`k`, :math:`M_m` the atomic weight of element :math:`m`,
 |      :math:`M_k` the molecular weight of species :math:`k`, and :math:`Y_k`
 |      the mass fraction of species :math:`k`.
 |      
 |      :param m:
 |          Base element, may be specified by name or by index.
 |      
 |      >>> phase.elemental_mass_fraction('H')
 |      1.0
 |  
 |  elemental_mole_fraction(...)
 |      ThermoPhase.elemental_mole_fraction(self, m)
 |      
 |      Get the elemental mole fraction :math:`Z_{\mathrm{mole},m}` of element
 |      :math:`m` (the number of atoms of element m divided by the total number
 |      of atoms) as defined by:
 |      
 |      .. math:: Z_{\mathrm{mole},m} = \frac{\sum_k a_{m,k} X_k}
 |                                           {\sum_k \sum_j a_{j,k} X_k}
 |      
 |      with :math:`a_{m,k}` being the number of atoms of element :math:`m` in
 |      species :math:`k`, :math:`\sum_j` being a sum over all elements, and
 |      :math:`X_k` being the mole fraction of species :math:`k`.
 |      
 |      :param m:
 |          Base element, may be specified by name or by index.
 |      
 |      >>> phase.elemental_mole_fraction('H')
 |      1.0
 |  
 |  equilibrate(...)
 |      ThermoPhase.equilibrate(self, XY, solver='auto', double rtol=1e-9, int maxsteps=1000, int maxiter=100, int estimate_equil=0, int loglevel=0)
 |      
 |      Set to a state of chemical equilibrium holding property pair
 |      *XY* constant.
 |      
 |      :param XY:
 |          A two-letter string, which must be one of the set::
 |      
 |              ['TP','TV','HP','SP','SV','UV']
 |      
 |      :param solver:
 |          Specifies the equilibrium solver to use. May be one of the following:
 |      
 |          * ''element_potential'' - a fast solver using the element potential
 |            method
 |          * 'gibbs' - a slower but more robust Gibbs minimization solver
 |          * 'vcs' - the VCS non-ideal equilibrium solver
 |          * "auto" - The element potential solver will be tried first, then
 |            if it fails the Gibbs solver will be tried.
 |      :param rtol:
 |          the relative error tolerance.
 |      :param maxsteps:
 |          maximum number of steps in composition to take to find a converged
 |          solution.
 |      :param maxiter:
 |          For the Gibbs minimization solver, this specifies the number of
 |          'outer' iterations on T or P when some property pair other
 |          than TP is specified.
 |      :param estimate_equil:
 |          Integer indicating whether the solver should estimate its own
 |          initial condition. If 0, the initial mole fraction vector in the
 |          ThermoPhase object is used as the initial condition. If 1, the
 |          initial mole fraction vector is used if the element abundances are
 |          satisfied. If -1, the initial mole fraction vector is thrown out,
 |          and an estimate is formulated.
 |      :param loglevel:
 |          Set to a value > 0 to write diagnostic output.
 |  
 |  get_equivalence_ratio(...)
 |      ThermoPhase.get_equivalence_ratio(self, oxidizers=[], ignore=[])
 |      
 |      Get the composition of a fuel/oxidizer mixture. This gives the
 |      equivalence ratio of an unburned mixture. This is not a quantity that is
 |      conserved after oxidation. Considers the oxidation of C to CO2, H to H2O
 |      and S to SO2. Other elements are assumed not to participate in oxidation
 |      (i.e. N ends up as N2).
 |       :param oxidizers:
 |          List of oxidizer species names as strings. Default: with
 |          ``oxidizers=[]``, every species that contains O but does not contain
 |          H, C, or S is considered to be an oxidizer.
 |      :param ignore:
 |          List of species names as strings to ignore.
 |       >>> gas.set_equivalence_ratio(0.5, 'CH3:0.5, CH3OH:.5, N2:0.125', 'O2:0.21, N2:0.79, NO:0.01')
 |      >>> gas.get_equivalence_ratio()
 |      0.50000000000000011
 |      >>> gas.get_equivalence_ratio(['O2'])  # Only consider O2 as the oxidizer instead of O2 and NO
 |      0.48809523809523814
 |      >>> gas.X = 'CH4:1, O2:2, NO:0.1'
 |      >>> gas.get_equivalence_ratio(ignore=['NO'])
 |      1.0
 |  
 |  mass_fraction_dict(...)
 |      ThermoPhase.mass_fraction_dict(self, double threshold=0.0)
 |  
 |  modify_species(...)
 |      ThermoPhase.modify_species(self, k, Species species)
 |  
 |  mole_fraction_dict(...)
 |      ThermoPhase.mole_fraction_dict(self, double threshold=0.0)
 |  
 |  n_atoms(...)
 |      ThermoPhase.n_atoms(self, species, element)
 |      
 |      Number of atoms of element *element* in species *species*. The element
 |      and species may be specified by name or by index.
 |      
 |      >>> phase.n_atoms('CH4','H')
 |      4
 |  
 |  report(...)
 |      ThermoPhase.report(self, show_thermo=True, float threshold=1e-14)
 |      
 |      Generate a report describing the thermodynamic state of this phase. To
 |      print the report to the terminal, simply call the phase object. The
 |      following two statements are equivalent::
 |      
 |      >>> phase()
 |      >>> print(phase.report())
 |  
 |  set_equivalence_ratio(...)
 |      ThermoPhase.set_equivalence_ratio(self, phi, fuel, oxidizer)
 |      
 |      Set the composition to a mixture of *fuel* and *oxidizer* at the
 |      specified equivalence ratio *phi*, holding temperature and pressure
 |      constant. Considers the oxidation of C and H to CO2 and H2O. Other
 |      elements are assumed not to participate in oxidation (i.e. N ends up as
 |      N2)::
 |      
 |          >>> gas.set_equivalence_ratio(0.5, 'CH4', 'O2:1.0, N2:3.76')
 |          >>> gas.mole_fraction_dict()
 |          {'CH4': 0.049900199, 'N2': 0.750499001, 'O2': 0.199600798}
 |      
 |          >>> gas.set_equivalence_ratio(1.2, {'NH3;:0.8, 'CO':0.2}, 'O2:1.0')
 |          >>> gas.mole_fraction_dict()
 |          {'CO': 0.1263157894, 'NH3': 0.505263157, 'O2': 0.36842105}
 |      
 |      :param phi: Equivalence ratio
 |      :param fuel:
 |          Fuel species name or molar composition as string, array, or dict.
 |      :param oxidizer:
 |          Oxidizer species name or molar composition as a string, array, or
 |          dict.
 |  
 |  set_unnormalized_mass_fractions(...)
 |      ThermoPhase.set_unnormalized_mass_fractions(self, Y)
 |      
 |      Set the mass fractions without normalizing to force sum(Y) == 1.0.
 |      Useful primarily when calculating derivatives with respect to Y[k] by
 |      finite difference.
 |  
 |  set_unnormalized_mole_fractions(...)
 |      ThermoPhase.set_unnormalized_mole_fractions(self, X)
 |      
 |      Set the mole fractions without normalizing to force sum(X) == 1.0.
 |      Useful primarily when calculating derivatives with respect to X[k]
 |      by finite difference.
 |  
 |  species(...)
 |      ThermoPhase.species(self, k=None)
 |      
 |      Return the `Species` object for species *k*, where *k* is either the
 |      species index or the species name. If *k* is not specified, a list of
 |      all species objects is returned.
 |  
 |  species_index(...)
 |      ThermoPhase.species_index(self, species) -> int
 |      
 |      The index of species *species*, which may be specified as a string or
 |      an integer. In the latter case, the index is checked for validity and
 |      returned. If no such species is present, an exception is thrown.
 |  
 |  species_name(...)
 |      ThermoPhase.species_name(self, k)
 |      Name of the species with index *k*.
 |  
 |  ----------------------------------------------------------------------
 |  Static methods inherited from cantera._cantera.ThermoPhase:
 |  
 |  __new__(*args, **kwargs) from builtins.type
 |      Create and return a new object.  See help(type) for accurate signature.
 |  
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from cantera._cantera.ThermoPhase:
 |  
 |  DP
 |      Get/Set density [kg/m^3] and pressure [Pa].
 |  
 |  DPX
 |      Get/Set density [kg/m^3], pressure [Pa], and mole fractions.
 |  
 |  DPY
 |      Get/Set density [kg/m^3], pressure [Pa], and mass fractions.
 |  
 |  HP
 |      Get/Set enthalpy [J/kg or J/kmol] and pressure [Pa].
 |  
 |  HPX
 |      Get/Set enthalpy [J/kg or J/kmol], pressure [Pa] and mole fractions.
 |  
 |  HPY
 |      Get/Set enthalpy [J/kg or J/kmol], pressure [Pa] and mass fractions.
 |  
 |  ID
 |      The ID of the phase. The default is taken from the CTI/XML input file.
 |  
 |  P
 |      Pressure [Pa].
 |  
 |  P_sat
 |      Saturation pressure [Pa] at the current temperature.
 |  
 |  SP
 |      Get/Set entropy [J/kg/K or J/kmol/K] and pressure [Pa].
 |  
 |  SPX
 |      Get/Set entropy [J/kg/K or J/kmol/K], pressure [Pa], and mole fractions.
 |  
 |  SPY
 |      Get/Set entropy [J/kg/K or J/kmol/K], pressure [Pa], and mass fractions.
 |  
 |  SV
 |      Get/Set entropy [J/kg/K or J/kmol/K] and specific volume [m^3/kg or
 |      m^3/kmol].
 |  
 |  SVX
 |      Get/Set entropy [J/kg/K or J/kmol/K], specific volume [m^3/kg or
 |      m^3/kmol], and mole fractions.
 |  
 |  SVY
 |      Get/Set entropy [J/kg/K or J/kmol/K], specific volume [m^3/kg or
 |      m^3/kmol], and mass fractions.
 |  
 |  T
 |      Temperature [K].
 |  
 |  TD
 |      Get/Set temperature [K] and density [kg/m^3 or kmol/m^3].
 |  
 |  TDX
 |      Get/Set temperature [K], density [kg/m^3 or kmol/m^3], and mole
 |      fractions.
 |  
 |  TDY
 |      Get/Set temperature [K] and density [kg/m^3 or kmol/m^3], and mass
 |      fractions.
 |  
 |  TP
 |      Get/Set temperature [K] and pressure [Pa].
 |  
 |  TPX
 |      Get/Set temperature [K], pressure [Pa], and mole fractions.
 |  
 |  TPY
 |      Get/Set temperature [K], pressure [Pa], and mass fractions.
 |  
 |  T_sat
 |      Saturation temperature [K] at the current pressure.
 |  
 |  UV
 |      Get/Set internal energy [J/kg or J/kmol] and specific volume
 |      [m^3/kg or m^3/kmol].
 |  
 |  UVX
 |      Get/Set internal energy [J/kg or J/kmol], specific volume
 |      [m^3/kg or m^3/kmol], and mole fractions.
 |  
 |  UVY
 |      Get/Set internal energy [J/kg or J/kmol], specific volume
 |      [m^3/kg or m^3/kmol], and mass fractions.
 |  
 |  X
 |      Get/Set the species mole fractions. Can be set as an array, as a dictionary,
 |      or as a string. Always returns an array::
 |      
 |          >>> phase.X = [0.1, 0, 0, 0.4, 0, 0, 0, 0, 0.5]
 |          >>> phase.X = {'H2':0.1, 'O2':0.4, 'AR':0.5}
 |          >>> phase.X = 'H2:0.1, O2:0.4, AR:0.5'
 |          >>> phase.X
 |          array([0.1, 0, 0, 0.4, 0, 0, 0, 0, 0.5])
 |  
 |  Y
 |      Get/Set the species mass fractions. Can be set as an array, as a dictionary,
 |      or as a string. Always returns an array::
 |      
 |          >>> phase.Y = [0.1, 0, 0, 0.4, 0, 0, 0, 0, 0.5]
 |          >>> phase.Y = {'H2':0.1, 'O2':0.4, 'AR':0.5}
 |          >>> phase.Y = 'H2:0.1, O2:0.4, AR:0.5'
 |          >>> phase.Y
 |          array([0.1, 0, 0, 0.4, 0, 0, 0, 0, 0.5])
 |  
 |  atomic_weights
 |      Array of atomic weight [kg/kmol] for each element in the mixture.
 |  
 |  basis
 |      Determines whether intensive thermodynamic properties are treated on a
 |      `mass` (per kg) or `molar` (per kmol) basis. This affects the values
 |      returned by the properties `h`, `u`, `s`, `g`, `v`, `density`, `cv`,
 |      and `cp`, as well as the values used with the state-setting properties
 |      such as `HPX` and `UV`.
 |  
 |  chemical_potentials
 |      Array of species chemical potentials [J/kmol].
 |  
 |  concentrations
 |      Get/Set the species concentrations [kmol/m^3].
 |  
 |  cp
 |      Heat capacity at constant pressure [J/kg/K or J/kmol/K] depending
 |      on `basis`.
 |  
 |  cp_mass
 |      Specific heat capacity at constant pressure [J/kg/K].
 |  
 |  cp_mole
 |      Molar heat capacity at constant pressure [J/kmol/K].
 |  
 |  critical_density
 |      Critical density [kg/m^3 or kmol/m^3] depending on `basis`.
 |  
 |  critical_pressure
 |      Critical pressure [Pa].
 |  
 |  critical_temperature
 |      Critical temperature [K].
 |  
 |  cv
 |      Heat capacity at constant volume [J/kg/K or J/kmol/K] depending on
 |      `basis`.
 |  
 |  cv_mass
 |      Specific heat capacity at constant volume [J/kg/K].
 |  
 |  cv_mole
 |      Molar heat capacity at constant volume [J/kmol/K].
 |  
 |  density
 |      Density [kg/m^3 or kmol/m^3] depending on `basis`.
 |  
 |  density_mass
 |      (Mass) density [kg/m^3].
 |  
 |  density_mole
 |      Molar density [kmol/m^3].
 |  
 |  electric_potential
 |      Get/Set the electric potential [V] for this phase.
 |  
 |  electrochemical_potentials
 |      Array of species electrochemical potentials [J/kmol].
 |  
 |  element_names
 |      A list of all the element names.
 |  
 |  enthalpy_mass
 |      Specific enthalpy [J/kg].
 |  
 |  enthalpy_mole
 |      Molar enthalpy [J/kmol].
 |  
 |  entropy_mass
 |      Specific entropy [J/kg].
 |  
 |  entropy_mole
 |      Molar entropy [J/kmol/K].
 |  
 |  g
 |      Gibbs free energy [J/kg or J/kmol] depending on `basis`.
 |  
 |  gibbs_mass
 |      Specific Gibbs free energy [J/kg].
 |  
 |  gibbs_mole
 |      Molar Gibbs free energy [J/kmol].
 |  
 |  h
 |      Enthalpy [J/kg or J/kmol] depending on `basis`.
 |  
 |  int_energy_mass
 |      Specific internal energy [J/kg].
 |  
 |  int_energy_mole
 |      Molar internal energy [J/kmol].
 |  
 |  isothermal_compressibility
 |      Isothermal compressibility [1/Pa].
 |  
 |  max_temp
 |      Maximum temperature for which the thermodynamic data for the phase are
 |      valid.
 |  
 |  mean_molecular_weight
 |      The mean molecular weight (molar mass) [kg/kmol].
 |  
 |  min_temp
 |      Minimum temperature for which the thermodynamic data for the phase are
 |      valid.
 |  
 |  molecular_weights
 |      Array of species molecular weights (molar masses) [kg/kmol].
 |  
 |  n_elements
 |      Number of elements.
 |  
 |  n_selected_species
 |      Number of species selected for output (by slicing of Solution object)
 |  
 |  n_species
 |      Number of species.
 |  
 |  name
 |      The name assigned to this phase. The default is taken from the CTI/XML
 |      input file.
 |  
 |  partial_molar_cp
 |      Array of species partial molar specific heat capacities at constant
 |      pressure [J/kmol/K].
 |  
 |  partial_molar_enthalpies
 |      Array of species partial molar enthalpies [J/kmol].
 |  
 |  partial_molar_entropies
 |      Array of species partial molar entropies [J/kmol/K].
 |  
 |  partial_molar_int_energies
 |      Array of species partial molar internal energies [J/kmol].
 |  
 |  partial_molar_volumes
 |      Array of species partial molar volumes [m^3/kmol].
 |  
 |  reference_pressure
 |      Reference state pressure [Pa].
 |  
 |  s
 |      Entropy [J/kg/K or J/kmol/K] depending on `basis`.
 |  
 |  species_names
 |      A list of all the species names.
 |  
 |  standard_cp_R
 |      Array of nondimensional species standard-state specific heat capacities
 |      at constant pressure at the current temperature and pressure.
 |  
 |  standard_enthalpies_RT
 |      Array of nondimensional species standard-state enthalpies at the
 |      current temperature and pressure.
 |  
 |  standard_entropies_R
 |      Array of nondimensional species standard-state entropies at the
 |      current temperature and pressure.
 |  
 |  standard_gibbs_RT
 |      Array of nondimensional species standard-state Gibbs free energies at
 |      the current temperature and pressure.
 |  
 |  standard_int_energies_RT
 |      Array of nondimensional species standard-state internal energies at the
 |      current temperature and pressure.
 |  
 |  state
 |      Get/Set the full thermodynamic state as a single array, arranged as
 |      [temperature, density, mass fractions] for most phases. Useful mainly
 |      in cases where it is desired to store many states in a multidimensional
 |      array.
 |  
 |  thermal_expansion_coeff
 |      Thermal expansion coefficient [1/K].
 |  
 |  u
 |      Internal energy in [J/kg or J/kmol].
 |  
 |  v
 |      Specific volume [m^3/kg or m^3/kmol] depending on `basis`.
 |  
 |  volume_mass
 |      Specific volume [m^3/kg].
 |  
 |  volume_mole
 |      Molar volume [m^3/kmol].
 |  
 |  ----------------------------------------------------------------------
 |  Data and other attributes inherited from cantera._cantera.ThermoPhase:
 |  
 |  __pyx_vtable__ = <capsule object NULL>
 |  
 |  ----------------------------------------------------------------------
 |  Methods inherited from cantera._cantera.Kinetics:
 |  
 |  add_reaction(...)
 |      Kinetics.add_reaction(self, Reaction rxn)
 |      Add a new reaction to this phase.
 |  
 |  is_reversible(...)
 |      Kinetics.is_reversible(self, int i_reaction)
 |      True if reaction `i_reaction` is reversible.
 |  
 |  kinetics_species_index(...)
 |      Kinetics.kinetics_species_index(self, species, int phase=0)
 |      
 |      The index of species *species* of phase *phase* within arrays returned
 |      by methods of class `Kinetics`. If *species* is a string, the *phase*
 |      argument is unused.
 |  
 |  modify_reaction(...)
 |      Kinetics.modify_reaction(self, int irxn, Reaction rxn)
 |      
 |      Modify the `Reaction` with index ``irxn`` to have the same rate
 |      parameters as ``rxn``. ``rxn`` must have the same reactants and products
 |      and be of the same type (i.e. `ElementaryReaction`, `FalloffReaction`,
 |      `PlogReaction`, etc.) as the existing reaction. This method does not
 |      modify the third-body efficiencies, reaction orders, or reversibility of
 |      the reaction.
 |  
 |  multiplier(...)
 |      Kinetics.multiplier(self, int i_reaction)
 |      
 |      A scaling factor applied to the rate coefficient for reaction
 |      *i_reaction*. Can be used to carry out sensitivity analysis or to
 |      selectively disable a particular reaction. See `set_multiplier`.
 |  
 |  product_stoich_coeff(...)
 |      Kinetics.product_stoich_coeff(self, k_spec, int i_reaction)
 |      
 |      The stoichiometric coefficient of species *k_spec* as a product in
 |      reaction *i_reaction*.
 |  
 |  product_stoich_coeffs(...)
 |      Kinetics.product_stoich_coeffs(self)
 |      
 |      The array of product stoichiometric coefficients. Element *[k,i]* of
 |      this array is the product stoichiometric coefficient of species *k* in
 |      reaction *i*.
 |  
 |  products(...)
 |      Kinetics.products(self, int i_reaction)
 |      The products portion of the reaction equation
 |  
 |  reactant_stoich_coeff(...)
 |      Kinetics.reactant_stoich_coeff(self, k_spec, int i_reaction)
 |      
 |      The stoichiometric coefficient of species *k_spec* as a reactant in
 |      reaction *i_reaction*.
 |  
 |  reactant_stoich_coeffs(...)
 |      Kinetics.reactant_stoich_coeffs(self)
 |      
 |      The array of reactant stoichiometric coefficients. Element *[k,i]* of
 |      this array is the reactant stoichiometric coefficient of species *k* in
 |      reaction *i*.
 |  
 |  reactants(...)
 |      Kinetics.reactants(self, int i_reaction)
 |      The reactants portion of the reaction equation
 |  
 |  reaction(...)
 |      Kinetics.reaction(self, int i_reaction)
 |      
 |      Return a `Reaction` object representing the reaction with index
 |      ``i_reaction``.
 |  
 |  reaction_equation(...)
 |      Kinetics.reaction_equation(self, int i_reaction)
 |      The equation for the specified reaction. See also `reaction_equations`.
 |  
 |  reaction_equations(...)
 |      Kinetics.reaction_equations(self, indices=None)
 |      
 |      Returns a list containing the reaction equation for all reactions in the
 |      mechanism (if *indices* is unspecified) or the equations for each
 |      reaction in the sequence *indices*. For example::
 |      
 |          >>> gas.reaction_equations()
 |          ['2 O + M <=> O2 + M', 'O + H + M <=> OH + M', 'O + H2 <=> H + OH', ...]
 |          >>> gas.reaction_equations([2,3])
 |          ['O + H + M <=> OH + M', 'O + H2 <=> H + OH']
 |      
 |      See also `reaction_equation`.
 |  
 |  reaction_type(...)
 |      Kinetics.reaction_type(self, int i_reaction)
 |      Type of reaction *i_reaction*.
 |  
 |  reactions(...)
 |      Kinetics.reactions(self)
 |      
 |      Return a list of all `Reaction` objects
 |  
 |  reset_custom(...)
 |      Kinetics.reset_custom(self)
 |      
 |      Function calling the dlclose in CustomKinetics
 |      in order to close the dynamic library (handle)
 |  
 |  set_multiplier(...)
 |      Kinetics.set_multiplier(self, double value, int i_reaction=-1)
 |      
 |      Set the multiplier for for reaction *i_reaction* to *value*.
 |      If *i_reaction* is not specified, then the multiplier for all reactions
 |      is set to *value*. See `multiplier`.
 |  
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from cantera._cantera.Kinetics:
 |  
 |  creation_rates
 |      Creation rates for each species. [kmol/m^3/s] for bulk phases or
 |      [kmol/m^2/s] for surface phases.
 |  
 |  delta_enthalpy
 |      Change in enthalpy for each reaction [J/kmol].
 |  
 |  delta_entropy
 |      Change in entropy for each reaction [J/kmol/K].
 |  
 |  delta_gibbs
 |      Change in Gibbs free energy for each reaction [J/kmol].
 |  
 |  delta_standard_enthalpy
 |      Change in standard-state enthalpy (independent of composition) for
 |      each reaction [J/kmol].
 |  
 |  delta_standard_entropy
 |      Change in standard-state entropy (independent of composition) for
 |      each reaction [J/kmol/K].
 |  
 |  delta_standard_gibbs
 |      Change in standard-state Gibbs free energy (independent of composition)
 |      for each reaction [J/kmol].
 |  
 |  destruction_rates
 |      Destruction rates for each species. [kmol/m^3/s] for bulk phases or
 |      [kmol/m^2/s] for surface phases.
 |  
 |  equilibrium_constants
 |      Equilibrium constants in concentration units for all reactions.
 |  
 |  forward_rate_constants
 |      Forward rate constants for all reactions. Units are a combination of
 |      kmol, m^3 and s, that depend on the rate expression for the reaction.
 |  
 |  forward_rates_of_progress
 |      Forward rates of progress for the reactions. [kmol/m^3/s] for bulk
 |      phases or [kmol/m^2/s] for surface phases.
 |  
 |  n_phases
 |      Number of phases in the reaction mechanism.
 |  
 |  n_reactions
 |      Number of reactions in the reaction mechanism.
 |  
 |  n_total_species
 |      Total number of species in all phases participating in the kinetics
 |      mechanism.
 |  
 |  net_production_rates
 |      Net production rates for each species. [kmol/m^3/s] for bulk phases or
 |      [kmol/m^2/s] for surface phases.
 |  
 |  net_rates_of_progress
 |      Net rates of progress for the reactions. [kmol/m^3/s] for bulk phases
 |      or [kmol/m^2/s] for surface phases.
 |  
 |  reaction_phase_index
 |      The index of the phase where the reactions occur.
 |  
 |  reverse_rate_constants
 |      Reverse rate constants for all reactions. Units are a combination of
 |      kmol, m^3 and s, that depend on the rate expression for the reaction.
 |  
 |  reverse_rates_of_progress
 |      Reverse rates of progress for the reactions. [kmol/m^3/s] for bulk
 |      phases or [kmol/m^2/s] for surface phases.
 |  
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from cantera._cantera.Transport:
 |  
 |  binary_diff_coeffs
 |      Binary diffusion coefficients [m^2/s].
 |  
 |  electrical_conductivity
 |      Electrical conductivity. [S/m].
 |  
 |  mix_diff_coeffs
 |      Mixture-averaged diffusion coefficients [m^2/s] relating the
 |      mass-averaged diffusive fluxes (with respect to the mass averaged
 |      velocity) to gradients in the species mole fractions.
 |  
 |  mix_diff_coeffs_mass
 |      Mixture-averaged diffusion coefficients [m^2/s] relating the
 |      diffusive mass fluxes to gradients in the species mass fractions.
 |  
 |  mix_diff_coeffs_mole
 |      Mixture-averaged diffusion coefficients [m^2/s] relating the
 |      molar diffusive fluxes to gradients in the species mole fractions.
 |  
 |  multi_diff_coeffs
 |      Multicomponent diffusion coefficients [m^2/s].
 |  
 |  species_viscosities
 |      Pure species viscosities [Pa-s]
 |  
 |  thermal_conductivity
 |      Thermal conductivity. [W/m/K].
 |  
 |  thermal_diff_coeffs
 |      Return a one-dimensional array of the species thermal diffusion
 |      coefficients [kg/m/s].
 |  
 |  transport_model
 |      Get/Set the transport model associated with this transport model.
 |      
 |      Setting a new transport model deletes the underlying C++ Transport
 |      object and replaces it with a new one implementing the specified model.
 |  
 |  viscosity
 |      Viscosity [Pa-s].
 |  
 |  ----------------------------------------------------------------------
 |  Methods inherited from cantera._cantera._SolutionBase:
 |  
 |  __copy__(...)
 |      _SolutionBase.__copy__(self)
 |  
 |  __getitem__(self, key, /)
 |      Return self[key].
 |  
 |  __reduce__(...)
 |      _SolutionBase.__reduce__(self)
 |  
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from cantera._cantera._SolutionBase:
 |  
 |  selected_species

You can use several functions to define the state of your gas, that is to say :

  • gas.TP (Temperature Pressure)
  • gas.TD (Temperature Density)
  • gas.HP (Enthalpy Pressure)
  • gas.UV (Specific Internal Energy, Specific Volume)
  • gas.SP (Entropy Pressure)
  • gas.SV (Entropy Specific Volume).
In [4]:
gas.TP = 500, 101325

Wrong method

Here, we chose to define the molar fraction of the gas directly by the following :

In [5]:
gas.X = {'CH4':1, 'O2':2, 'N2':7.52}
In [6]:
print(gas())
  gri30:

       temperature             500  K
          pressure         7391.79  Pa
           density       0.0491334  kg/m^3
  mean mol. weight         27.6332  amu

                          1 kg            1 kmol
                       -----------      ------------
          enthalpy          -33317       -9.207e+05     J
   internal energy     -1.8376e+05       -5.078e+06     J
           entropy          8599.3        2.376e+05     J/K
    Gibbs function      -4.333e+06       -1.197e+08     J
 heat capacity c_p          1140.4        3.151e+04     J/K
 heat capacity c_v          839.54         2.32e+04     J/K

                           X                 Y          Chem. Pot. / RT
                     -------------     ------------     ------------
                O2       0.190114         0.220149         -29.3581
               CH4       0.095057        0.0551863         -45.8564
                N2       0.714829         0.724665         -26.3852
     [  +50 minor]              0                0

None

What do you notice here ? Look at the pressure : it is not the same than what has been define above. You should never defined pressure and temperature and call the command "gas.Y" afterwards. Below are explained correct methods to set the case correctly.

First method

In [9]:
gas.TPX = 500, 101325, {'CH4':1, 'O2':2, 'N2':7.52}
In [10]:
print(gas())
  gri30:

       temperature             500  K
          pressure          101325  Pa
           density         0.67351  kg/m^3
  mean mol. weight         27.6332  amu

                          1 kg            1 kmol
                       -----------      ------------
          enthalpy          -33317       -9.207e+05     J
   internal energy     -1.8376e+05       -5.078e+06     J
           entropy          7811.6        2.159e+05     J/K
    Gibbs function     -3.9391e+06       -1.089e+08     J
 heat capacity c_p          1140.4        3.151e+04     J/K
 heat capacity c_v          839.54         2.32e+04     J/K

                           X                 Y          Chem. Pot. / RT
                     -------------     ------------     ------------
                O2       0.190114         0.220149         -26.7401
               CH4       0.095057        0.0551863         -43.2384
                N2       0.714829         0.724665         -23.7672
     [  +50 minor]              0                0

None

Second method

Here, we will set an equivalence ratio equal to unity with a mix of fuel (CH4) and oxidizer (air), which is doing the same as above.

In [11]:
gas.TP = 500, 101325
In [12]:
gas.set_equivalence_ratio(1, 'CH4: 1', 'O2:1.0, N2:3.76')
In [13]:
print(gas())
  gri30:

       temperature             500  K
          pressure          101325  Pa
           density         0.67351  kg/m^3
  mean mol. weight         27.6332  amu

                          1 kg            1 kmol
                       -----------      ------------
          enthalpy          -33317       -9.207e+05     J
   internal energy     -1.8376e+05       -5.078e+06     J
           entropy          7811.6        2.159e+05     J/K
    Gibbs function     -3.9391e+06       -1.089e+08     J
 heat capacity c_p          1140.4        3.151e+04     J/K
 heat capacity c_v          839.54         2.32e+04     J/K

                           X                 Y          Chem. Pot. / RT
                     -------------     ------------     ------------
                O2       0.190114         0.220149         -26.7401
               CH4       0.095057        0.0551863         -43.2384
                N2       0.714829         0.724665         -23.7672
     [  +50 minor]              0                0

None

Additional informations

In [14]:
print(gas.species_names)
['H2', 'H', 'O', 'O2', 'OH', 'H2O', 'HO2', 'H2O2', 'C', 'CH', 'CH2', 'CH2(S)', 'CH3', 'CH4', 'CO', 'CO2', 'HCO', 'CH2O', 'CH2OH', 'CH3O', 'CH3OH', 'C2H', 'C2H2', 'C2H3', 'C2H4', 'C2H5', 'C2H6', 'HCCO', 'CH2CO', 'HCCOH', 'N', 'NH', 'NH2', 'NH3', 'NNH', 'NO', 'NO2', 'N2O', 'HNO', 'CN', 'HCN', 'H2CN', 'HCNN', 'HCNO', 'HOCN', 'HNCO', 'NCO', 'N2', 'AR', 'C3H7', 'C3H8', 'CH2CHO', 'CH3CHO']
In [15]:
print(gas.species_index('CO2'))
15

Other informations concerning functions associated to the thermodynamic properties of the gas object can be found on the help function or on the following link :
https://cantera.org/documentation/docs-2.4/sphinx/html/cython/thermo.html

4. Kinetic state of the gas

As well as for the thermodynamic state of the gas, the kinetic state can be found at the following link :
https://cantera.org/documentation/docs-2.4/sphinx/html/cython/kinetics.html

In [16]:
print(gas.net_production_rates)
[ 0.00000000e+00  3.47828430e-33  9.56902897e-36 -1.90362750e-19
  0.00000000e+00  0.00000000e+00  1.90362750e-19  0.00000000e+00
  0.00000000e+00  0.00000000e+00  0.00000000e+00  0.00000000e+00
  1.90362750e-19 -1.90362750e-19  0.00000000e+00  0.00000000e+00
  0.00000000e+00  0.00000000e+00  0.00000000e+00  0.00000000e+00
  0.00000000e+00  0.00000000e+00  0.00000000e+00  0.00000000e+00
  0.00000000e+00  0.00000000e+00  0.00000000e+00  0.00000000e+00
  0.00000000e+00  0.00000000e+00  0.00000000e+00  0.00000000e+00
  0.00000000e+00  0.00000000e+00  9.36554123e-42  0.00000000e+00
  0.00000000e+00  9.56902877e-36  0.00000000e+00  0.00000000e+00
  0.00000000e+00  0.00000000e+00  0.00000000e+00  0.00000000e+00
  0.00000000e+00  0.00000000e+00  0.00000000e+00 -9.56903814e-36
  0.00000000e+00  0.00000000e+00  0.00000000e+00  0.00000000e+00
  0.00000000e+00]

Here, this is nearly zero as no reaction has occured in the mix.

5. Transport properties

For the transport, the functions can be found here :
https://cantera.org/documentation/docs-2.4/sphinx/html/cython/transport.html

In [17]:
print(gas.binary_diff_coeffs)
---------------------------------------------------------------------------
CanteraError                              Traceback (most recent call last)
<ipython-input-17-569894f894e1> in <module>
----> 1 print(gas.binary_diff_coeffs)

interfaces/cython/cantera/transport.pyx in cantera._cantera.Transport.binary_diff_coeffs.__get__()

interfaces/cython/cantera/transport.pyx in cantera._cantera.get_transport_2d()

CanteraError: 
***********************************************************************
NotImplementedError thrown by Transport::getBinaryDiffCoeffs:
Not implemented.
***********************************************************************

The code throws an error, which is pretty normal as nothing chemical was computed for the moment. The gas object created is indeed just a mix of different species, nothing has reacted (explaining the kinetics net production rates nearly close to zero and the transport properties not implemented).

Here, with the version we used at CERFACS, four types of transport are available. The four differs in the following way :

  • multi is the most complicated and detailed version, it uses each diffusion coefficient $D_{kj}$ to represent the interaction between each species (k being a species and j another one).
  • mix is the most used version in Cantera as it allows the user to approximate results without losing too much precision. The approximation made is that every species has one interaction with the whole mix following the rule : $D_{km} = \frac{1-Y_k}{\sum_{j\ne k}^{K} \frac{X_j}{Djk}}$.
  • AVBP which is the transport used to compare results with AVBP solver used at cerfacs (this transport is not included in the normal version). This supposes a constant Schmidt number ( $Sc = \frac{\rho}{\mu D_{km}}$, $\rho$ being the density and $\mu$ the viscosity ) for all the species and $D_{km}$ is guessed from this relation.
  • UnityLewis which has been implemented in the official release 2.4 of Cantera but integrated in CERFACS version 2.3.

https://cantera.org/science/phases.html

This types of transport are used in the cti file, as you will see in a minute.

Conclusion

The purpose of this part was to explain :

  • how one can set up the thermodynamic state of a gas for a computation
  • how one will be able to print interesting data from the gaseous object
    In the next part, we will focus on the object used to created the cantera gas object : the cti file.

Things to retain from the first tutorial :

  • you should always import Cantera at the beginning of your file.
  • the solution is imported from a cti file or an xml file.
  • you should set the thermodynamic state and the amount of species of your gas before starting any computation.

Appendix : The cti and xml files

a. Creation of the data file from CHEMKIN files

The information required to compute the previous quantities were specified in the .xml file, also labeled mechanism file or data file. Cantera also supports a data file format that is easier to write than the '.xml' format, with the extension '.cti'.
For the following part, you can open a cti script in the Mechanisms folder (for instance the gri30 mechanism) to have a visual idea of what is a cti file.

Cantera simulations will always involve one or more phases of matter. Depending on the calculation being performed, it may be necessary to evaluate thermodynamic properties, but also transport properties, and/or homogeneous reaction rates for the phase(s) present. In problems with multiple phases, the properties of the interfaces between phases, and the heterogeneous reaction rates at these interfaces, may also be required.

Before the properties can be evaluated, each phase must be defined, meaning that the models used to compute its properties and reaction rates must be specified, along with any parameters the models require. For example, a solid phase might be defined as being incompressible, with a specified density and composition. A gaseous phase for a combustion simulation might be defined as an ideal gas consisting of a mixture of many species that react with one another via a specified set of reactions.
If phases contain multiple species and reactions, as it is often the case in combustion application, a large amount of data is required to define it, since the contribution of each species to the thermodynamic and transport properties must be specified, and rate information must be given for each reaction. Rather than defining this information via an application program, the Cantera approach is to put the phase and interface definitions in a text file that can be called from and read by an application program - or a script.

In this tutorial, we will review what must be included in such 'data files', or 'mechanism files', and provide guidelines on how to write them to define phases and interfaces to use them in Cantera simulations. We will start by a review of some basic writing rules, followed by a discussion on how they are processed, and of how errors are handled. We will work with examples in the last sections.

To be able to translate the files from chemkin (mechanism file, thermo database and transport database) to cantera (data file), it is necessary to use the command ck2cti.
Normally, this command should be executed on a terminal. Here, the python script is used as an inbetween, therefore calling the subprocess module is needed. If you look into the folder now, the data file mechanism should be created.

In [18]:
ck2cti.convertMech('CK2CTI/mech.inp', thermoFile='CK2CTI/therm.dat', transportFile='CK2CTI/tran.dat', outName=None, permissive=None)
INFO:root:Skipping unexpected species "C(S)" while reading thermodynamics entry.
INFO:root:Skipping unexpected species "n-C4H7" while reading thermodynamics entry.
INFO:root:Skipping unexpected species "c-C6H3" while reading thermodynamics entry.
INFO:root:Skipping unexpected species "A1C2HC2H2" while reading thermodynamics entry.
INFO:root:Skipping unexpected species "A2HR5" while reading thermodynamics entry.
INFO:root:Skipping unexpected species "A2R5" while reading thermodynamics entry.
INFO:root:Skipping unexpected species "A4H" while reading thermodynamics entry.
Wrote CTI mechanism file to 'CK2CTI/mech.cti'.
Mechanism contains 99 species and 533 reactions.
Out[18]:
[]

b. The .cti file

The typical shape of a **cti** file will be the following :

UNITS DIRECTIVE

Phase & Interface data

PHASE ENTRIES(name, elements, species, reactions, kinetics, transport, initial_state*, options)
INTERFACE ENTRIES(name, elements, species, reactions, phases, site_density, initial_state*)

Species & Elements data

ELEMENT ENTRIES(symbol, atomic_mass) SPECIES ENTRIES(name, atoms, thermo ,transport, note, size, charge)

Reaction data

REACTION ENTRIES(equation, rate_coeff, id, options)
THREE BODY REACTIONS ENTRIES(equation, rate_coeff, efficiencies, id, options)
FALLOFF REACTIONS ENTRIES(equation, rate_coeff_inf, rate_coeff_0, efficiencies, falloff, id, options)
OTHER TYPES OF ENTRIES ...

A data file consists of entries and directives, both of which have a syntax much like functions.

A directive will tell the code how the entry parameters are to be interpreted, such as what is the default unit system, or how certain errors should be handled. For example :

units(length = "cm", time = "s", quantity = "mol", act_energy = "cal/mol")

An entry defines an object, for example, a reaction or a species. Entries have fields, that can be assigned values. Take the definition of the argon species :

species(name = "AR", atoms = " Ar:1 ", thermo = ( NASA( [ 300.00, 1000.00], [ 2.500000000E+00, 0.000000000E+00, 0.000000000E+00, 0.000000000E+00, 0.000000000E+00, -7.453750000E+02, 4.366000000E+00] ), NASA( [ 1000.00, 5000.00], [ 2.500000000E+00, 0.000000000E+00, 0.000000000E+00, 0.000000000E+00, 0.000000000E+00, -7.453750000E+02, 4.366000000E+00] ) ), transport = gas_transport( geom = "atom", diam = 3.33, well_depth = 136.50), )

Its fields are its name, atoms, thermodynamic and transport properties.
The syntax is < field name > = < value > , and the fields can be specified on one line or extended across several to be read more easily, as it was the case in the previous example. Some fields are required, otherwise processing the file will abort and an error message will be printed.
As can be seen on this example, the transport field for instance is defined via another entry, gas transport, which in turn has several fields (geom, diam, well depth). These types of entries are embedded entries, whereas the leftmost column entries are labeled top-level entries. Embedded entries often specify a model or a large group of parameters.

A cti file can support three different types of reactions :

  • classic reactions reaction() (classic Arrhenius defined like equations)
  • three-body reactions three_body_reaction() (reactions involving another species which can be a probability of being one species or another)
  • falloff_reaction fall_off_reaction() (three-body reactions whose rates k are depending on the concentration of the three-body)

If you want more documentation about the reactions in cantera, please follow the link below :
https://cantera.org/science/reactions.html

NB : The following link will provide you other information about the species data if you are interested in knowing more about it :
https://cantera.org/science/science-species.html

In [ ]: