def save(self, outputFile): """ Save the results of the kinetics job to the file located at `path` on disk. """ reaction = self.reaction ks = [] k0s = [] k0revs = [] krevs = [] logging.info('Saving kinetics for {0}...'.format(reaction)) order = len(self.reaction.reactants) factor = 1e6 ** (order-1) f = open(outputFile, 'a') if self.usedTST: # If TST is not used, eg. it was given in 'reaction', then this will throw an error. f.write('# ======= =========== =========== =========== ===============\n') f.write('# Temp. k (TST) Tunneling k (TST+T) Units\n') f.write('# ======= =========== =========== =========== ===============\n') if self.Tlist is None: Tlist = numpy.array([300,400,500,600,800,1000,1500,2000]) else: Tlist =self.Tlist.value_si for T in Tlist: tunneling = reaction.transitionState.tunneling reaction.transitionState.tunneling = None try: k0 = reaction.calculateTSTRateCoefficient(T) * factor except SpeciesError: k0 = 0 reaction.transitionState.tunneling = tunneling try: k = reaction.calculateTSTRateCoefficient(T) * factor kappa = k / k0 except (SpeciesError,ZeroDivisionError): k = reaction.getRateCoefficient(T) kappa = 0 logging.info("The species in reaction {} do not have adequate information for TST, using default kinetics values.".format(reaction)) tunneling = reaction.transitionState.tunneling ks.append(k) k0s.append(k0) f.write('# {0:4g} K {1:11.3e} {2:11g} {3:11.3e} {4}\n'.format(T, k0, kappa, k, self.kunits)) f.write('# ======= =========== =========== =========== ===============\n') f.write('\n\n') f.write('# ======= ============ =========== ============ ============= =========\n') f.write('# Temp. Kc (eq) Units krev (TST) krev (TST+T) Units\n') f.write('# ======= ============ =========== ============ ============= =========\n') # Initialize Object for Converting Units if self.Kequnits != ' ': keq_unit_converter = quantity.Units(self.Kequnits).getConversionFactorFromSI() else: keq_unit_converter = 1 for n,T in enumerate(Tlist): k = ks[n] k0 = k0s[n] Keq = keq_unit_converter * reaction.getEquilibriumConstant(T) # getEquilibriumConstant returns SI units k0rev = k0/Keq krev = k/Keq k0revs.append(k0rev) krevs.append(krev) f.write('# {0:4g} K {1:11.3e} {2} {3:11.3e} {4:11.3e} {5}\n'.format(T, Keq, self.Kequnits, k0rev, krev, self.krunits)) f.write('# ======= ============ =========== ============ ============= =========\n') f.write('\n\n') kinetics0rev = Arrhenius().fitToData(Tlist, numpy.array(k0revs), kunits=self.krunits) kineticsrev = Arrhenius().fitToData(Tlist, numpy.array(krevs), kunits=self.krunits) f.write('# krev (TST) = {0} \n'.format(kinetics0rev)) f.write('# krev (TST+T) = {0} \n\n'.format(kineticsrev)) # Reaction path degeneracy is INCLUDED in the kinetics itself! string = 'kinetics(label={0!r}, kinetics={1!r})'.format(reaction.label, reaction.kinetics) f.write('{0}\n\n'.format(prettify(string))) f.close() # Also save the result to chem.inp f = open(os.path.join(os.path.dirname(outputFile), 'chem.inp'), 'a') reaction = self.reaction kinetics = reaction.kinetics string = '' if reaction.kinetics.comment: for line in reaction.kinetics.comment.split("\n"): string += "! {0}\n".format(line) string += '{0!s:51} {1:9.3e} {2:9.3f} {3:9.3f}\n'.format( reaction, kinetics.A.value_si * factor, kinetics.n.value_si, kinetics.Ea.value_si / 4184., ) f.write('{0}\n'.format(string)) f.close() # We're saving a YAML file for TSs iff structures of the respective reactant/s and product/s are known if all ([spc.molecule is not None and len(spc.molecule) for spc in self.reaction.reactants + self.reaction.products]): self.arkane_species.update_species_attributes(self.reaction.transitionState) self.arkane_species.reaction_label = reaction.label self.arkane_species.reactants = [{'label': spc.label, 'adjacency_list': spc.molecule[0].toAdjacencyList()} for spc in self.reaction.reactants] self.arkane_species.products = [{'label': spc.label, 'adjacency_list': spc.molecule[0].toAdjacencyList()} for spc in self.reaction.products] self.arkane_species.save_yaml(path=os.path.dirname(outputFile))
def write_output(self, output_directory): """ Save the results of the kinetics job to the `output.py` file located in `output_directory`. """ reaction = self.reaction ks, k0s, k0_revs, k_revs = [], [], [], [] logging.info('Saving kinetics for {0}...'.format(reaction)) order = len(self.reaction.reactants) factor = 1e6**(order - 1) f = open(os.path.join(output_directory, 'output.py'), 'a') if self.usedTST: # If TST is not used, eg. it was given in 'reaction', then this will throw an error. f.write( '# ======= =========== =========== =========== ===============\n' ) f.write('# Temp. k (TST) Tunneling k (TST+T) Units\n') f.write( '# ======= =========== =========== =========== ===============\n' ) if self.Tlist is None: t_list = np.array([300, 400, 500, 600, 800, 1000, 1500, 2000]) else: t_list = self.Tlist.value_si for T in t_list: tunneling = reaction.transition_state.tunneling reaction.transition_state.tunneling = None try: k0 = reaction.calculate_tst_rate_coefficient(T) * factor except SpeciesError: k0 = 0 reaction.transition_state.tunneling = tunneling try: k = reaction.calculate_tst_rate_coefficient(T) * factor kappa = k / k0 except (SpeciesError, ZeroDivisionError): k = reaction.get_rate_coefficient(T) kappa = 0 logging.info( "The species in reaction {0} do not have adequate information for TST, " "using default kinetics values.".format(reaction)) tunneling = reaction.transition_state.tunneling ks.append(k) k0s.append(k0) f.write( '# {0:4g} K {1:11.3e} {2:11g} {3:11.3e} {4}\n'.format( T, k0, kappa, k, self.k_units)) f.write( '# ======= =========== =========== =========== ===============\n' ) f.write('\n\n') f.write( '# ======= ============ =========== ============ ============= =========\n' ) f.write( '# Temp. Kc (eq) Units k_rev (TST) k_rev (TST+T) Units\n' ) f.write( '# ======= ============ =========== ============ ============= =========\n' ) # Initialize Object for Converting Units if self.K_eq_units != ' ': keq_unit_converter = quantity.Units( self.K_eq_units).get_conversion_factor_from_si() else: keq_unit_converter = 1 for n, T in enumerate(t_list): k = ks[n] k0 = k0s[n] K_eq = keq_unit_converter * reaction.get_equilibrium_constant( T) # returns SI units k0_rev = k0 / K_eq k_rev = k / K_eq k0_revs.append(k0_rev) k_revs.append(k_rev) f.write( '# {0:4g} K {1:11.3e} {2} {3:11.3e} {4:11.3e} {5}\n' .format(T, K_eq, self.K_eq_units, k0_rev, k_rev, self.k_r_units)) f.write( '# ======= ============ =========== ============ ============= =========\n' ) f.write('\n\n') kinetics_0_rev = Arrhenius().fit_to_data(t_list, np.array(k0_revs), kunits=self.k_r_units) kinetics_rev = Arrhenius().fit_to_data(t_list, np.array(k_revs), kunits=self.k_r_units) f.write('# k_rev (TST) = {0} \n'.format(kinetics_0_rev)) f.write('# k_rev (TST+T) = {0} \n\n'.format(kinetics_rev)) # Reaction path degeneracy is INCLUDED in the kinetics itself! rxn_str = 'kinetics(label={0!r}, kinetics={1!r})'.format( reaction.label, reaction.kinetics) f.write('{0}\n\n'.format(prettify(rxn_str))) f.close()